001 //$HeadURL: svn+ssh://jwilden@svn.wald.intevation.org/deegree/base/branches/2.5_testing/src/org/deegree/crs/components/Axis.java $
002 /*----------------------------------------------------------------------------
003 This file is part of deegree, http://deegree.org/
004 Copyright (C) 2001-2009 by:
005 Department of Geography, University of Bonn
006 and
007 lat/lon GmbH
008
009 This library is free software; you can redistribute it and/or modify it under
010 the terms of the GNU Lesser General Public License as published by the Free
011 Software Foundation; either version 2.1 of the License, or (at your option)
012 any later version.
013 This library is distributed in the hope that it will be useful, but WITHOUT
014 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
015 FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more
016 details.
017 You should have received a copy of the GNU Lesser General Public License
018 along with this library; if not, write to the Free Software Foundation, Inc.,
019 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
020
021 Contact information:
022
023 lat/lon GmbH
024 Aennchenstr. 19, 53177 Bonn
025 Germany
026 http://lat-lon.de/
027
028 Department of Geography, University of Bonn
029 Prof. Dr. Klaus Greve
030 Postfach 1147, 53001 Bonn
031 Germany
032 http://www.geographie.uni-bonn.de/deegree/
033
034 e-mail: info@deegree.org
035 ----------------------------------------------------------------------------*/
036
037 package org.deegree.crs.components;
038
039 import java.io.Serializable;
040
041 /**
042 * The <code>Axis</code> class describe the orientation, unit and the name of a crs-axis.
043 *
044 * @author <a href="mailto:bezema@lat-lon.de">Rutger Bezema</a>
045 *
046 * @author last edited by: $Author: mschneider $
047 *
048 * @version $Revision: 18195 $, $Date: 2009-06-18 17:55:39 +0200 (Do, 18 Jun 2009) $
049 *
050 */
051
052 public class Axis implements Serializable {
053
054 private static final long serialVersionUID = -4527409382797041807L;
055
056 /**
057 * Axis is pointing NORTH ( == -SOUTH) e.g Polar axis positive northwards.
058 */
059 public static final int AO_NORTH = 1;
060
061 /**
062 * Axis is pointing SOUTH ( == -NORTH )
063 */
064 public static final int AO_SOUTH = -AO_NORTH;
065
066 /**
067 * Axis is pointing WEST( == -EAST)
068 */
069 public static final int AO_WEST = 2;
070
071 /**
072 * Axis is pointing EAST( == -WEST) the intersection of the equator with longitude 90°E.
073 */
074 public static final int AO_EAST = -AO_WEST;
075
076 /**
077 * Axis is pointing UP ( == -DOWN ),
078 */
079 public static final int AO_UP = 3;
080
081 /**
082 * Axis is pointing DOWN ( == -UP)
083 */
084 public static final int AO_DOWN = -AO_UP;
085
086 /**
087 * Axis is pointing FRONT( == -BACK), e.g. the Axis through the intersection of the Greenwich meridian and equator.
088 */
089 public static final int AO_FRONT = 4;
090
091 /**
092 * Axis is pointing BACK ( == -FRONT) e.g. the Axis through the intersection of the opposite of the Greenwich
093 * meridian and equator.
094 */
095 public static final int AO_BACK = -AO_FRONT;
096
097 /**
098 * Axis is pointing PERPENDICULAR to the earth's surface, which is used for a vertical axis.
099 */
100 public static final int AO_PERPENDICULAR = 5;
101
102 /**
103 * Axis is pointing in an OTHER direction, which is not specified.
104 */
105 public static final int AO_OTHER = Integer.MAX_VALUE;
106
107 private Unit units;
108
109 private String name;
110
111 private int orientation;
112
113 /**
114 * @param units
115 * of this axis
116 * @param name
117 * of this axis (e.g. longitude...)
118 * @param orientation
119 * of the positive scale direction, one of Axis.AO*. If an unknown value is supplied AO_OTHER is assumed.
120 */
121 public Axis( Unit units, String name, final int orientation ) {
122 this.units = units;
123 this.name = name;
124 this.orientation = orientation;
125 if ( orientation != AO_NORTH && orientation != AO_SOUTH && orientation != AO_WEST && orientation != AO_EAST
126 && orientation != AO_UP && orientation != AO_DOWN && orientation != AO_FRONT && orientation != AO_BACK
127 && orientation != AO_PERPENDICULAR ) {
128 this.orientation = AO_OTHER;
129 }
130
131 }
132
133 /**
134 * Parses the given orientation and creates a valid orientation of it's non-case-sensitive version. If no conversion
135 * was found, {@link #AO_OTHER} will be used.
136 *
137 * @param units
138 * of the axis.
139 * @param name
140 * of the axis.
141 * @param orientation
142 * of the axis as a string for example north
143 */
144 public Axis( Unit units, String name, String orientation ) {
145 this.units = units;
146 this.name = name;
147 this.orientation = AO_OTHER;
148 if ( orientation != null ) {
149 String tmp = orientation.trim().toLowerCase();
150 if ( tmp.contains( "north" ) ) {
151 this.orientation = AO_NORTH;
152 } else if ( tmp.contains( "south" ) ) {
153 this.orientation = AO_SOUTH;
154 } else if ( tmp.contains( "east" ) ) {
155 this.orientation = AO_EAST;
156 } else if ( tmp.contains( "west" ) ) {
157 this.orientation = AO_WEST;
158 } else if ( tmp.contains( "front" ) ) {
159 this.orientation = AO_FRONT;
160 } else if ( tmp.contains( "back" ) ) {
161 this.orientation = AO_BACK;
162 } else if ( tmp.contains( "up" ) ) {
163 this.orientation = AO_UP;
164 } else if ( tmp.contains( "down" ) ) {
165 this.orientation = AO_DOWN;
166 } else if ( tmp.contains( "perpendicular" ) ) {
167 this.orientation = AO_PERPENDICULAR;
168 }
169 }
170 }
171
172 /**
173 * An Axis with unit set to metre.
174 *
175 * @param name
176 * of this axis (e.g. longitude...)
177 * @param orientation
178 * of the positive scale direction, one of Axis.AO*. If an unknown value is supplied AO_OTHER is assumed.
179 */
180 public Axis( String name, final int orientation ) {
181 this( Unit.METRE, name, orientation );
182 }
183
184 /**
185 * Parses the given orientation and creates a valid orientation of it's non-case-sensitive version. If no conversion
186 * was found, {@link #AO_OTHER} will be used. This axis will have metres as it's unit.
187 *
188 * @param name
189 * of the axis
190 * @param orientation
191 * of the axis as a string for example north
192 */
193 public Axis( String name, final String orientation ) {
194 this( Unit.METRE, name, orientation );
195 }
196
197 /**
198 * @return the name.
199 */
200 public final String getName() {
201 return name;
202 }
203
204 /**
205 * @return the orientation.
206 */
207 public final int getOrientation() {
208 return orientation;
209 }
210
211 /**
212 * @return the units.
213 */
214 public final Unit getUnits() {
215 return units;
216 }
217
218 @Override
219 public String toString() {
220 return new StringBuilder( "name: " ).append( name ).append( " orientation: " ).append( getOrientationAsString() ).append(
221 " units: " ).append(
222 units ).toString();
223 }
224
225 @Override
226 public boolean equals( Object otherAxis ) {
227 if ( otherAxis == null || !( otherAxis instanceof Axis ) ) {
228 return false;
229 }
230 Axis other = (Axis) otherAxis;
231 return this.units.equals( other.units ) && this.orientation == other.orientation;
232 }
233
234 /**
235 * Implementation as proposed by Joshua Block in Effective Java (Addison-Wesley 2001), which supplies an even
236 * distribution and is relatively fast. It is created from field <b>f</b> as follows:
237 * <ul>
238 * <li>boolean -- code = (f ? 0 : 1)</li>
239 * <li>byte, char, short, int -- code = (int)f</li>
240 * <li>long -- code = (int)(f ^ (f >>>32))</li>
241 * <li>float -- code = Float.floatToIntBits(f);</li>
242 * <li>double -- long l = Double.doubleToLongBits(f); code = (int)(l ^ (l >>> 32))</li>
243 * <li>all Objects, (where equals( ) calls equals( ) for this field) -- code = f.hashCode( )</li>
244 * <li>Array -- Apply above rules to each element</li>
245 * </ul>
246 * <p>
247 * Combining the hash code(s) computed above: result = 37 * result + code;
248 * </p>
249 *
250 * @return (int) ( result >>> 32 ) ^ (int) result;
251 *
252 * @see java.lang.Object#hashCode()
253 */
254 @Override
255 public int hashCode() {
256 // the 2nd millionth prime, :-)
257 long code = 32452843;
258 if ( units != null ) {
259 code = code * 37 + units.hashCode();
260 }
261 long tmp = Double.doubleToLongBits( orientation );
262 code = code * 37 + (int) ( tmp ^ ( tmp >>> 32 ) );
263 return (int) ( code >>> 32 ) ^ (int) code;
264 }
265
266 /**
267 * @return an 'English' representation for the Axis Orientation, or Unknown if the given direction is not known.
268 */
269 public String getOrientationAsString() {
270 switch ( orientation ) {
271 case AO_NORTH:
272 return "north";
273 case AO_SOUTH:
274 return "south";
275 case AO_EAST:
276 return "east";
277 case AO_WEST:
278 return "west";
279 case AO_FRONT:
280 return "front";
281 case AO_BACK:
282 return "back";
283 case AO_UP:
284 return "up";
285 case AO_DOWN:
286 return "down";
287 case AO_OTHER:
288 return "Other";
289 case AO_PERPENDICULAR:
290 return "perpendicular";
291 }
292 return "Unknown";
293 }
294
295 }