001// License: GPL. For details, see LICENSE file. 002package org.openstreetmap.josm.gui.dialogs.changeset; 003 004import java.util.ArrayList; 005import java.util.Collections; 006import java.util.Comparator; 007import java.util.HashSet; 008import java.util.Iterator; 009import java.util.List; 010import java.util.Set; 011 012import javax.swing.DefaultListSelectionModel; 013import javax.swing.table.AbstractTableModel; 014 015import org.openstreetmap.josm.data.osm.ChangesetDataSet; 016import org.openstreetmap.josm.data.osm.ChangesetDataSet.ChangesetDataSetEntry; 017import org.openstreetmap.josm.data.osm.ChangesetDataSet.ChangesetModificationType; 018import org.openstreetmap.josm.data.osm.history.HistoryOsmPrimitive; 019 020/** 021 * This is the table model for the content of a changeset. 022 * 023 */ 024public class ChangesetContentTableModel extends AbstractTableModel { 025 026 private final List<ChangesetContentEntry> data = new ArrayList<ChangesetContentEntry>(); 027 private DefaultListSelectionModel selectionModel; 028 029 public ChangesetContentTableModel(DefaultListSelectionModel selectionModel) { 030 this.selectionModel = selectionModel; 031 } 032 033 /** 034 * Replies true if there is at least one selected primitive in the table model 035 * 036 * @return true if there is at least one selected primitive in the table model 037 */ 038 public boolean hasSelectedPrimitives() { 039 return selectionModel.getMinSelectionIndex() >= 0; 040 } 041 042 public void setSelectedByIdx(int row) { 043 selectionModel.setSelectionInterval(row, row); 044 } 045 046 /** 047 * Replies the selection model 048 * @return the selection model 049 */ 050 public DefaultListSelectionModel getSelectionModel() { 051 return selectionModel; 052 } 053 054 public Set<HistoryOsmPrimitive> getSelectedPrimitives() { 055 Set<HistoryOsmPrimitive> ret = new HashSet<HistoryOsmPrimitive>(); 056 for (int i=0;i < data.size();i++) { 057 if (selectionModel.isSelectedIndex(i)) { 058 ret.add(data.get(i).getPrimitive()); 059 } 060 } 061 return ret; 062 } 063 064 /** 065 * Populates the model with the content of a model. If ds is null, the 066 * table is cleared. 067 * 068 * @param ds the changeset content. 069 */ 070 public void populate(ChangesetDataSet ds) { 071 this.data.clear(); 072 if (ds == null) { 073 fireTableDataChanged(); 074 return; 075 } 076 for (Iterator<ChangesetDataSetEntry> it = ds.iterator(); it.hasNext();) { 077 data.add(new ChangesetContentEntry(it.next())); 078 } 079 sort(); 080 fireTableDataChanged(); 081 } 082 083 protected void sort() { 084 Collections.sort( 085 data, 086 new Comparator<ChangesetDataSetEntry>() { 087 @Override 088 public int compare(ChangesetDataSetEntry c1, ChangesetDataSetEntry c2) { 089 if (c1.getModificationType().equals(c2.getModificationType())) { 090 long id1 = c1.getPrimitive().getId(); 091 long id2 = c2.getPrimitive().getId(); 092 093 if (id1 == id2) 094 return 0; 095 else if (id1 < id2) 096 return -1; 097 return 1; 098 } 099 switch(c1.getModificationType()) { 100 case CREATED: return -1; 101 case UPDATED: 102 switch(c2.getModificationType()) { 103 case CREATED: return 1; 104 default: return -1; 105 } 106 case DELETED: 107 return 1; 108 } 109 // should not happen 110 return 0; 111 } 112 } 113 ); 114 } 115 116 /* -------------------------------------------------------------- */ 117 /* interface TableModel */ 118 /* -------------------------------------------------------------- */ 119 @Override 120 public int getColumnCount() { 121 return 3; 122 } 123 124 @Override 125 public int getRowCount() { 126 return data.size(); 127 } 128 129 @Override 130 public Object getValueAt(int row, int col) { 131 switch(col) { 132 case 0: return data.get(row).getModificationType(); 133 default: return data.get(row).getPrimitive(); 134 } 135 } 136 137 /** 138 * The type used internally to keep information about {@link HistoryOsmPrimitive} 139 * with their {@link ChangesetModificationType}. 140 * 141 */ 142 static private class ChangesetContentEntry implements ChangesetDataSetEntry{ 143 private final ChangesetModificationType modificationType; 144 private final HistoryOsmPrimitive primitive; 145 146 public ChangesetContentEntry(ChangesetModificationType modificationType, HistoryOsmPrimitive primitive) { 147 this.modificationType = modificationType; 148 this.primitive = primitive; 149 } 150 151 public ChangesetContentEntry(ChangesetDataSetEntry entry) { 152 this(entry.getModificationType(), entry.getPrimitive()); 153 } 154 155 @Override 156 public ChangesetModificationType getModificationType() { 157 return modificationType; 158 } 159 @Override 160 public HistoryOsmPrimitive getPrimitive() { 161 return primitive; 162 } 163 } 164}