001// License: GPL. For details, see LICENSE file. 002package org.openstreetmap.josm.data.osm; 003 004import static org.openstreetmap.josm.tools.I18n.marktr; 005import static org.openstreetmap.josm.tools.I18n.tr; 006 007import java.text.MessageFormat; 008import java.util.Arrays; 009import java.util.Collection; 010 011/** 012 * OSM primitive type. 013 * @since 1670 014 */ 015public enum OsmPrimitiveType { 016 017 /** Node type */ 018 NODE(marktr(/* ICON(data/) */"node"), Node.class, NodeData.class), 019 /** Way type */ 020 WAY(marktr(/* ICON(data/) */"way"), Way.class, WayData.class), 021 /** Relation type */ 022 RELATION(marktr(/* ICON(data/) */"relation"), Relation.class, RelationData.class), 023 024 /** Closed way: only for display, no real type */ 025 CLOSEDWAY(marktr(/* ICON(data/) */"closedway"), null, WayData.class), 026 /** Multipolygon: only for display, no real type */ 027 MULTIPOLYGON(marktr(/* ICON(data/) */"multipolygon"), null, RelationData.class); 028 029 private static final Collection<OsmPrimitiveType> DATA_VALUES = Arrays.asList(NODE, WAY, RELATION); 030 031 private final String apiTypeName; 032 private final Class<? extends OsmPrimitive> osmClass; 033 private final Class<? extends PrimitiveData> dataClass; 034 035 OsmPrimitiveType(String apiTypeName, Class<? extends OsmPrimitive> osmClass, Class<? extends PrimitiveData> dataClass) { 036 this.apiTypeName = apiTypeName; 037 this.osmClass = osmClass; 038 this.dataClass = dataClass; 039 } 040 041 /** 042 * Returns the API type name / JOSM display name. 043 * @return the API type name / JOSM display name 044 */ 045 public String getAPIName() { 046 return apiTypeName; 047 } 048 049 /** 050 * Returns the OSM class for data values, or null. 051 * @return the OSM class for data values, or null 052 */ 053 public Class<? extends OsmPrimitive> getOsmClass() { 054 return osmClass; 055 } 056 057 /** 058 * Returns the data class. 059 * @return the data class 060 */ 061 public Class<? extends PrimitiveData> getDataClass() { 062 return dataClass; 063 } 064 065 /** 066 * Returns enum value from API type name / JOSM display name, case sensitive. 067 * @param typeName API type name / JOSM display name, case sensitive 068 * @return matching enum value 069 * @throws IllegalArgumentException if the type name does not match any valid type 070 * @see #from(String) 071 */ 072 public static OsmPrimitiveType fromApiTypeName(String typeName) { 073 for (OsmPrimitiveType type : OsmPrimitiveType.values()) { 074 if (type.getAPIName().equals(typeName)) return type; 075 } 076 throw new IllegalArgumentException(MessageFormat.format( 077 "Parameter ''{0}'' is not a valid type name. Got ''{1}''.", "typeName", typeName)); 078 } 079 080 /** 081 * Determines the OSM primitive type of the given object. 082 * @param obj the OSM object to inspect 083 * @return the OSM primitive type of {@code obj} 084 * @throws IllegalArgumentException if {@code obj} is null or of unknown type 085 */ 086 public static OsmPrimitiveType from(IPrimitive obj) { 087 if (obj instanceof INode) return NODE; 088 if (obj instanceof IWay) return WAY; 089 if (obj instanceof IRelation) return RELATION; 090 throw new IllegalArgumentException("Unknown type: "+obj); 091 } 092 093 /** 094 * Returns enum value from API type name / JOSM display name, case insensitive. 095 * @param value API type name / JOSM display name, case insensitive 096 * @return matching enum value or null 097 * @see #fromApiTypeName 098 */ 099 public static OsmPrimitiveType from(String value) { 100 for (OsmPrimitiveType type: values()) { 101 if (type.getAPIName().equalsIgnoreCase(value)) 102 return type; 103 } 104 return null; 105 } 106 107 /** 108 * Returns the values matching real OSM API data types (node, way, relation). 109 * @return the values matching real OSM API data types (node, way, relation) 110 */ 111 public static Collection<OsmPrimitiveType> dataValues() { 112 return DATA_VALUES; 113 } 114 115 /** 116 * Constructs a new primitive instance (node, way or relation) without version. 117 * @param uniqueId the unique id 118 * @param allowNegative {@code true} to allow negative id 119 * @return a new primitive instance (node, way or relation) 120 * @throws IllegalArgumentException if uniqueId < 0 and allowNegative is false 121 */ 122 public OsmPrimitive newInstance(long uniqueId, boolean allowNegative) { 123 switch (this) { 124 case NODE: 125 return new Node(uniqueId, allowNegative); 126 case WAY: 127 return new Way(uniqueId, allowNegative); 128 case RELATION: 129 return new Relation(uniqueId, allowNegative); 130 default: 131 throw new AssertionError(); 132 } 133 } 134 135 /** 136 * Constructs a new primitive instance (node, way or relation) with given version. 137 * @param id The id. Must be >= 0 138 * @param version The version 139 * @return a new primitive instance (node, way or relation) with given version 140 * @throws IllegalArgumentException if id < 0 141 * @since 12018 142 */ 143 public OsmPrimitive newVersionedInstance(long id, int version) { 144 switch (this) { 145 case NODE: 146 return new Node(id, version); 147 case WAY: 148 return new Way(id, version); 149 case RELATION: 150 return new Relation(id, version); 151 default: 152 throw new AssertionError(); 153 } 154 } 155 156 @Override 157 public String toString() { 158 return tr(getAPIName()); 159 } 160}