001 // License: GPL. For details, see LICENSE file.
002 package org.openstreetmap.josm.io.remotecontrol;
003
004 import static org.openstreetmap.josm.tools.I18n.tr;
005
006 import java.awt.Color;
007 import java.awt.Component;
008 import java.awt.Dimension;
009 import java.awt.Font;
010 import java.awt.GridBagLayout;
011 import java.awt.event.ActionEvent;
012 import java.util.Collection;
013
014 import javax.swing.JPanel;
015 import javax.swing.JTable;
016 import javax.swing.table.DefaultTableModel;
017 import javax.swing.table.TableCellRenderer;
018 import javax.swing.table.TableModel;
019
020 import org.openstreetmap.josm.Main;
021 import org.openstreetmap.josm.command.ChangePropertyCommand;
022 import org.openstreetmap.josm.data.SelectionChangedListener;
023 import org.openstreetmap.josm.data.osm.DataSet;
024 import org.openstreetmap.josm.data.osm.OsmPrimitive;
025 import org.openstreetmap.josm.gui.ExtendedDialog;
026 import org.openstreetmap.josm.tools.GBC;
027
028 /**
029 *
030 * @author master
031 *
032 * Dialog to add tags as part of the remotecontrol
033 * Existing Keys get grey color and unchecked selectboxes so they will not overwrite the old Key-Value-Pairs by default.
034 * You can choose the tags you want to add by selectboxes. You can edit the tags before you apply them.
035 *
036 */
037 public class AddTagsDialog extends ExtendedDialog implements SelectionChangedListener {
038
039
040 private final JTable propertyTable;
041 private Collection<? extends OsmPrimitive> sel;
042 boolean[] existing;
043
044 public AddTagsDialog(String[][] tags) {
045 super(Main.parent, tr("Add tags to selected objects"), new String[] { tr("Add tags"), tr("Cancel")},
046 false,
047 true);
048
049 DataSet.addSelectionListener(this);
050
051
052 DefaultTableModel tm = new DefaultTableModel(new String[] {tr("Assume"), tr("Key"), tr("Value")}, tags.length) {
053 @Override
054 public Class getColumnClass(int c) {
055 return getValueAt(0, c).getClass();
056 }
057
058 };
059
060 sel = Main.main.getCurrentDataSet().getSelected();
061 existing = new boolean[tags.length];
062
063 for (int i = 0; i<tags.length; i++) {
064 existing[i] = false;
065 String key = tags[i][0];
066 Boolean b = Boolean.TRUE;
067 for (OsmPrimitive osm : sel) {
068 if (osm.keySet().contains(key)) {
069 b = Boolean.FALSE;
070 existing[i]=true;
071 break;
072 }
073 }
074 tm.setValueAt(b, i, 0);
075 tm.setValueAt(tags[i][0], i, 1);
076 tm.setValueAt(tags[i][1], i, 2);
077 }
078
079 propertyTable = new JTable(tm) {
080
081 private static final long serialVersionUID = 1L;
082
083 @Override
084 public Component prepareRenderer(TableCellRenderer renderer, int row, int column) {
085 Component c = super.prepareRenderer(renderer, row, column);
086 if (existing[row]) {
087 c.setFont(c.getFont().deriveFont(Font.ITALIC));
088 c.setForeground(new Color(100, 100, 100));
089 } else {
090 c.setFont(c.getFont().deriveFont(Font.PLAIN));
091 c.setForeground(new Color(0, 0, 0));
092 }
093 return c;
094 }
095 };
096
097 // a checkbox has a size of 15 px
098 propertyTable.getColumnModel().getColumn(0).setMaxWidth(15);
099 // get edit results if the table looses the focus, for example if a user clicks "add tags"
100 propertyTable.putClientProperty("terminateEditOnFocusLost", Boolean.TRUE);
101
102 // set the content of this AddTagsDialog consisting of the tableHeader and the table itself.
103 JPanel tablePanel = new JPanel();
104 tablePanel.setLayout(new GridBagLayout());
105 tablePanel.add(propertyTable.getTableHeader(), GBC.eol().fill(GBC.HORIZONTAL));
106 tablePanel.add(propertyTable, GBC.eol().fill(GBC.BOTH));
107 setContent(tablePanel);
108
109 // set the default Dimensions and show the dialog
110 setPreferredSize(new Dimension(400,tablePanel.getPreferredSize().height+100));
111 showDialog();
112 }
113
114 /**
115 * This method looks for existing tags in the current selection and sets the corresponding boolean in the boolean array existing[]
116 */
117 private void findExistingTags() {
118 TableModel tm = propertyTable.getModel();
119 for (int i=0; i<tm.getRowCount(); i++) {
120 String key = (String)tm.getValueAt(i, 1);
121 existing[i] = false;
122 for (OsmPrimitive osm : sel) {
123 if (osm.keySet().contains(key)) {
124 existing[i] = true;
125 break;
126 }
127 }
128 }
129 propertyTable.repaint();
130 }
131
132 /**
133 * If you click the "Add tags" button build a ChangePropertyCommand for every key that has a checked checkbox to apply the key value pair to all selected osm objects.
134 * You get a entry for every key in the command queue.
135 */
136 @Override
137 protected void buttonAction(int buttonIndex, ActionEvent evt) {
138 if (buttonIndex == 0) {
139 TableModel tm = propertyTable.getModel();
140 for (int i=0; i<tm.getRowCount(); i++) {
141 if ((Boolean)tm.getValueAt(i, 0)) {
142 Main.main.undoRedo.add(new ChangePropertyCommand(sel, (String)tm.getValueAt(i, 1), (String)tm.getValueAt(i, 2)));
143 }
144 }
145 }
146 setVisible(false);
147 }
148
149 @Override
150 public void selectionChanged(Collection<? extends OsmPrimitive> newSelection) {
151 sel = newSelection;
152 findExistingTags();
153 }
154
155 }