001// License: GPL. For details, see LICENSE file. 002package org.openstreetmap.josm.data.osm; 003 004import java.io.IOException; 005import java.io.ObjectInputStream; 006import java.io.ObjectOutputStream; 007import java.io.Serializable; 008import java.util.ArrayList; 009import java.util.Arrays; 010import java.util.Collection; 011import java.util.List; 012import java.util.Map; 013 014/** 015 * This class can be used to save properties of OsmPrimitive. 016 * 017 * The main difference between PrimitiveData 018 * and OsmPrimitive is that PrimitiveData is not part of the dataset and changes in PrimitiveData are not 019 * reported by events 020 */ 021public abstract class PrimitiveData extends AbstractPrimitive implements Serializable { 022 023 private static final long serialVersionUID = -1044837092478109138L; 024 025 /** 026 * Constructs a new {@code PrimitiveData}. 027 */ 028 public PrimitiveData() { 029 this(OsmPrimitive.generateUniqueId()); 030 } 031 032 /** 033 * Constructs a new {@code PrimitiveData} with given id. 034 * @param id id 035 * @since 12017 036 */ 037 public PrimitiveData(long id) { 038 this.id = id; 039 } 040 041 /** 042 * Constructs a new {@code PrimitiveData} from an existing one. 043 * @param data the data to copy 044 */ 045 public PrimitiveData(PrimitiveData data) { 046 cloneFrom(data); 047 } 048 049 /** 050 * Sets the primitive identifier. 051 * @param id primitive identifier 052 */ 053 public void setId(long id) { 054 this.id = id; 055 } 056 057 /** 058 * Sets the primitive version. 059 * @param version primitive version 060 */ 061 public void setVersion(int version) { 062 this.version = version; 063 } 064 065 /** 066 * override to make it public 067 */ 068 @Override 069 public void setIncomplete(boolean incomplete) { 070 super.setIncomplete(incomplete); 071 } 072 073 /** 074 * Returns a copy of this primitive data. 075 * @return a copy of this primitive data 076 */ 077 public abstract PrimitiveData makeCopy(); 078 079 @Override 080 public String toString() { 081 StringBuilder builder = new StringBuilder(); 082 builder.append(id).append(' ').append(Arrays.toString(keys)).append(' ').append(getFlagsAsString()); 083 return builder.toString(); 084 } 085 086 /** 087 * Returns a filtered list for a given primitive type. 088 * @param <T> primitive type 089 * @param list list to filter 090 * @param type primitive type 091 * @return a filtered list for given primitive type 092 */ 093 @SuppressWarnings("unchecked") 094 public static <T extends PrimitiveData> List<T> getFilteredList(Collection<T> list, OsmPrimitiveType type) { 095 List<T> ret = new ArrayList<>(); 096 for (PrimitiveData p: list) { 097 if (type.getDataClass().isInstance(p)) { 098 ret.add((T) p); 099 } 100 } 101 return ret; 102 } 103 104 @Override 105 protected final void keysChangedImpl(Map<String, String> originalKeys) { 106 } 107 108 private void writeObject(ObjectOutputStream oos) throws IOException { 109 // since super class is not Serializable 110 oos.writeLong(id); 111 oos.writeLong(user == null ? -1 : user.getId()); 112 oos.writeInt(version); 113 oos.writeInt(changesetId); 114 oos.writeInt(timestamp); 115 oos.writeObject(keys); 116 oos.writeShort(flags); 117 oos.defaultWriteObject(); 118 } 119 120 private void readObject(ObjectInputStream ois) throws ClassNotFoundException, IOException { 121 // since super class is not Serializable 122 id = ois.readLong(); 123 final long userId = ois.readLong(); 124 user = userId == -1 ? null : User.getById(userId); 125 version = ois.readInt(); 126 changesetId = ois.readInt(); 127 timestamp = ois.readInt(); 128 keys = (String[]) ois.readObject(); 129 flags = ois.readShort(); 130 ois.defaultReadObject(); 131 } 132}