Ignore:
Timestamp:
2012-12-20T22:43:02+01:00 (7 years ago)
Author:
jttt
Message:

use diff to show relation members in history dialog, jump to first change when different version is selected

Location:
trunk/src/org/openstreetmap/josm/gui/history
Files:
6 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/org/openstreetmap/josm/gui/history/DiffTableModel.java

    r5266 r5627  
    66
    77import javax.swing.table.AbstractTableModel;
     8
     9import org.openstreetmap.josm.gui.history.TwoColumnDiff.Item.DiffItemType;
    810
    911/**
     
    3941        return rows.get(rowIndex);
    4042    }
     43
     44    public int getFirstChange() {
     45        for (int i=0; i<rows.size(); i++) {
     46            if (rows.get(i).state != DiffItemType.SAME)
     47                return i;
     48        }
     49        return -1;
     50    }
    4151}
  • trunk/src/org/openstreetmap/josm/gui/history/HistoryBrowserModel.java

    r5495 r5627  
    4242import org.openstreetmap.josm.gui.MapView;
    4343import org.openstreetmap.josm.gui.MapView.LayerChangeListener;
     44import org.openstreetmap.josm.gui.history.TwoColumnDiff.Item.DiffItemType;
    4445import org.openstreetmap.josm.gui.layer.Layer;
    4546import org.openstreetmap.josm.gui.layer.OsmDataLayer;
     
    8687    private TagTableModel currentTagTableModel;
    8788    private TagTableModel referenceTagTableModel;
    88     private RelationMemberTableModel currentRelationMemberTableModel;
    89     private RelationMemberTableModel referenceRelationMemberTableModel;
     89    private DiffTableModel currentRelationMemberTableModel;
     90    private DiffTableModel referenceRelationMemberTableModel;
    9091    private DiffTableModel referenceNodeListTableModel;
    9192    private DiffTableModel currentNodeListTableModel;
     
    100101        referenceNodeListTableModel = new DiffTableModel();
    101102        currentNodeListTableModel = new DiffTableModel();
    102         currentRelationMemberTableModel = new RelationMemberTableModel(PointInTimeType.CURRENT_POINT_IN_TIME);
    103         referenceRelationMemberTableModel = new RelationMemberTableModel(PointInTimeType.REFERENCE_POINT_IN_TIME);
     103        currentRelationMemberTableModel = new DiffTableModel();
     104        referenceRelationMemberTableModel = new DiffTableModel();
    104105
    105106        if (getEditLayer() != null) {
     
    208209    protected void fireModelChange() {
    209210        initNodeListTableModels();
     211        initMemberListTableModels();
    210212        setChanged();
    211213        notifyObservers();
     
    247249
    248250    protected void initMemberListTableModels() {
     251        if(current.getType() != OsmPrimitiveType.RELATION || reference.getType() != OsmPrimitiveType.RELATION)
     252            return;
     253
     254        TwoColumnDiff diff = new TwoColumnDiff(
     255                ((HistoryRelation)reference).getMembers().toArray(),
     256                ((HistoryRelation)current).getMembers().toArray());
     257
     258        referenceRelationMemberTableModel.setRows(diff.referenceDiff);
     259        currentRelationMemberTableModel.setRows(diff.currentDiff);
     260
    249261        currentRelationMemberTableModel.fireTableDataChanged();
    250262        referenceRelationMemberTableModel.fireTableDataChanged();
     
    280292    }
    281293
    282     public RelationMemberTableModel getRelationMemberTableModel(PointInTimeType pointInTimeType) throws IllegalArgumentException {
     294    public DiffTableModel getRelationMemberTableModel(PointInTimeType pointInTimeType) throws IllegalArgumentException {
    283295        CheckParameterUtil.ensureParameterNotNull(pointInTimeType, "pointInTimeType");
    284296        if (pointInTimeType.equals(PointInTimeType.CURRENT_POINT_IN_TIME))
     
    429441                return isCurrentPointInTime(row);
    430442            case 3: {
    431                     HistoryOsmPrimitive p = getPrimitive(row);
    432                     if (p != null && p.getTimestamp() != null)
    433                         return DateFormat.getDateTimeInstance(DateFormat.SHORT, DateFormat.SHORT).format(p.getTimestamp());
    434                     return null;
     443                HistoryOsmPrimitive p = getPrimitive(row);
     444                if (p != null && p.getTimestamp() != null)
     445                    return DateFormat.getDateTimeInstance(DateFormat.SHORT, DateFormat.SHORT).format(p.getTimestamp());
     446                return null;
     447            }
     448            case 4: {
     449                HistoryOsmPrimitive p = getPrimitive(row);
     450                if (p != null) {
     451                    User user = p.getUser();
     452                    if (user != null)
     453                        return "<html>" + XmlWriter.encode(user.getName(), true) + " <font color=gray>(" + user.getId() + ")</font></html>";
    435454                }
    436             case 4: {
    437                     HistoryOsmPrimitive p = getPrimitive(row);
    438                     if (p != null) {
    439                         User user = p.getUser();
    440                         if (user != null)
    441                             return "<html>" + XmlWriter.encode(user.getName(), true) + " <font color=gray>(" + user.getId() + ")</font></html>";
    442                     }
    443                     return null;
    444                 }
     455                return null;
     456            }
    445457            }
    446458            return null;
     
    635647    }
    636648
    637     /**
    638      * The table model for the relation members of the version at {@link PointInTimeType#REFERENCE_POINT_IN_TIME}
    639      * or {@link PointInTimeType#CURRENT_POINT_IN_TIME}
    640      *
    641      */
    642 
    643     public class RelationMemberTableModel extends AbstractTableModel {
    644 
    645         private PointInTimeType pointInTimeType;
    646 
    647         private RelationMemberTableModel(PointInTimeType pointInTimeType) {
    648             this.pointInTimeType = pointInTimeType;
    649         }
    650 
    651         @Override
    652         public int getRowCount() {
    653             // Match the size of the opposite table so comparison is less confusing.
    654             // (scroll bars lines up properly, etc.)
    655             int n = 0;
    656             if (current != null && current.getType().equals(OsmPrimitiveType.RELATION)) {
    657                 n = ((HistoryRelation)current).getNumMembers();
    658             }
    659             if (reference != null && reference.getType().equals(OsmPrimitiveType.RELATION)) {
    660                 n = Math.max(n,((HistoryRelation)reference).getNumMembers());
    661             }
    662             return n;
    663         }
    664 
    665         protected HistoryRelation getRelation() {
    666             if (pointInTimeType.equals(PointInTimeType.CURRENT_POINT_IN_TIME)) {
    667                 if (! current.getType().equals(OsmPrimitiveType.RELATION))
    668                     return null;
    669                 return (HistoryRelation)current;
    670             }
    671             if (pointInTimeType.equals(PointInTimeType.REFERENCE_POINT_IN_TIME)) {
    672                 if (! reference.getType().equals(OsmPrimitiveType.RELATION))
    673                     return null;
    674                 return (HistoryRelation)reference;
    675             }
    676 
    677             // should not happen
    678             return null;
    679         }
    680 
    681         protected HistoryRelation getOppositeRelation() {
    682             PointInTimeType opposite = pointInTimeType.opposite();
    683             if (opposite.equals(PointInTimeType.CURRENT_POINT_IN_TIME)) {
    684                 if (! current.getType().equals(OsmPrimitiveType.RELATION))
    685                     return null;
    686                 return (HistoryRelation)current;
    687             }
    688             if (opposite.equals(PointInTimeType.REFERENCE_POINT_IN_TIME)) {
    689                 if (! reference.getType().equals(OsmPrimitiveType.RELATION))
    690                     return null;
    691                 return (HistoryRelation)reference;
    692             }
    693 
    694             // should not happen
    695             return null;
    696         }
    697 
    698         @Override
    699         public Object getValueAt(int row, int column) {
    700             HistoryRelation relation = getRelation();
    701             if (relation == null)
    702                 return null;
    703             if (row >= relation.getNumMembers()) // see getRowCount
    704                 return null;
    705             return relation.getMembers().get(row);
    706         }
    707 
    708         @Override
    709         public boolean isCellEditable(int row, int column) {
    710             return false;
    711         }
    712 
    713         public boolean isSameInOppositeWay(int row) {
    714             HistoryRelation thisRelation = getRelation();
    715             HistoryRelation oppositeRelation = getOppositeRelation();
    716             if (thisRelation == null || oppositeRelation == null)
    717                 return false;
    718             if (row >= oppositeRelation.getNumMembers())
    719                 return false;
    720             return
    721             thisRelation.getMembers().get(row).getMemberId() == oppositeRelation.getMembers().get(row).getMemberId()
    722             &&  thisRelation.getMembers().get(row).getRole().equals(oppositeRelation.getMembers().get(row).getRole());
    723         }
    724 
    725         public boolean isInOppositeWay(int row) {
    726             HistoryRelation thisRelation = getRelation();
    727             HistoryRelation oppositeRelation = getOppositeRelation();
    728             if (thisRelation == null || oppositeRelation == null)
    729                 return false;
    730             return oppositeRelation.getMembers().contains(thisRelation.getMembers().get(row));
    731         }
    732 
    733         @Override
    734         public int getColumnCount() {
    735             return 1;
    736         }
    737     }
    738 
    739649    protected void setLatest(HistoryOsmPrimitive latest) {
    740650        if (latest == null) {
  • trunk/src/org/openstreetmap/josm/gui/history/NodeListTableCellRenderer.java

    r4566 r5627  
    1212import javax.swing.table.TableCellRenderer;
    1313
     14import org.openstreetmap.josm.gui.history.TwoColumnDiff.Item.DiffItemType;
    1415import org.openstreetmap.josm.tools.ImageProvider;
    1516
    1617public class NodeListTableCellRenderer extends JLabel implements TableCellRenderer {
    1718
    18     public final static Color BGCOLOR_EMPTY_ROW = new Color(234,234,234);
    19     public final static Color BGCOLOR_DELETED = new Color(255,197,197);
    20     public final static Color BGCOLOR_INSERTED = new Color(0xDD, 0xFF, 0xDD);
    21     public final static Color BGCOLOR_CHANGED = new Color(255,234,213);
    2219    public final static Color BGCOLOR_SELECTED = new Color(143,170,255);
    2320
     
    3734            text = tr("Node {0}", item.value.toString());
    3835        }
    39         switch(item.state) {
    40         case TwoColumnDiff.Item.EMPTY:
     36        bgColor = item.state.getColor();
     37        if (item.state == DiffItemType.EMPTY) {
    4138            text = "";
    42             bgColor = BGCOLOR_EMPTY_ROW;
    4339            setIcon(null);
    44             break;
    45         case TwoColumnDiff.Item.CHANGED:
    46             bgColor = BGCOLOR_CHANGED;
    47             break;
    48         case TwoColumnDiff.Item.INSERTED:
    49             bgColor = BGCOLOR_INSERTED;
    50             break;
    51         case TwoColumnDiff.Item.DELETED:
    52             bgColor = BGCOLOR_DELETED;
    53             break;
    54         default:
    55             bgColor = BGCOLOR_EMPTY_ROW;
    5640        }
    5741        if (isSelected) {
  • trunk/src/org/openstreetmap/josm/gui/history/RelationMemberListTableCellRenderer.java

    r5266 r5627  
    1515import org.openstreetmap.josm.data.osm.OsmPrimitiveType;
    1616import org.openstreetmap.josm.data.osm.RelationMemberData;
     17import org.openstreetmap.josm.gui.history.TwoColumnDiff.Item;
    1718import org.openstreetmap.josm.tools.ImageProvider;
    1819
     
    4748    }
    4849
    49     protected void renderRole( HistoryBrowserModel.RelationMemberTableModel model, RelationMemberData member, int row, boolean isSelected) {
     50    protected void renderRole(Item diffItem, int row, boolean isSelected) {
    5051        String text = "";
    51         Color bgColor = Color.WHITE;
    52         if (member == null) {
    53             bgColor = BGCOLOR_EMPTY_ROW;
    54         } else {
    55             text = member.getRole();
    56             if (model.isSameInOppositeWay(row)) {
    57                 bgColor = Color.WHITE;
    58             } else if (model.isInOppositeWay(row)) {
    59                 bgColor = BGCOLOR_IN_OPPOSITE;
    60             } else {
    61                 bgColor = BGCOLOR_NOT_IN_OPPOSITE;
    62             }
    63         }
     52        Color bgColor = diffItem.state.getColor();
     53        RelationMemberData member = (RelationMemberData) diffItem.value;
     54        text = member == null?"":member.getRole();
    6455        setText(text);
    6556        setToolTipText(text);
     
    6758    }
    6859
    69     protected void renderPrimitive( HistoryBrowserModel.RelationMemberTableModel model, RelationMemberData member, int row, boolean isSelected) {
     60    protected void renderPrimitive(Item diffItem, int row, boolean isSelected) {
    7061        String text = "";
    71         Color bgColor = Color.WHITE;
    72         if (member == null) {
    73             bgColor = BGCOLOR_EMPTY_ROW;
    74         } else {
    75             text = "";
     62        Color bgColor = diffItem.state.getColor();
     63        RelationMemberData member = (RelationMemberData) diffItem.value;
     64        text = "";
     65        if (member != null) {
    7666            switch(member.getMemberType()) {
    7767            case NODE: text = tr("Node {0}", member.getMemberId()); break;
    7868            case WAY: text = tr("Way {0}", member.getMemberId()); break;
    7969            case RELATION: text = tr("Relation {0}", member.getMemberId()); break;
    80             }
    81             if (model.isSameInOppositeWay(row)) {
    82                 bgColor = Color.WHITE;
    83             } else if (model.isInOppositeWay(row)) {
    84                 bgColor = BGCOLOR_IN_OPPOSITE;
    85             } else {
    86                 bgColor = BGCOLOR_NOT_IN_OPPOSITE;
    8770            }
    8871        }
     
    9679            int row, int column) {
    9780
    98         HistoryBrowserModel.RelationMemberTableModel model = gteRelationMemberTableModel(table);
    99         RelationMemberData member = (RelationMemberData)value;
    100         renderIcon(member);
     81        Item member = (TwoColumnDiff.Item)value;
     82        renderIcon((RelationMemberData) member.value);
    10183        switch(column) {
    10284        case 0:
    103             renderRole(model, member, row, isSelected);
     85            renderRole(member, row, isSelected);
    10486            break;
    10587        case 1:
    106             renderPrimitive(model, member, row, isSelected);
     88            renderPrimitive(member, row, isSelected);
    10789            break;
    10890        }
     
    11193    }
    11294
    113     protected HistoryBrowserModel.RelationMemberTableModel gteRelationMemberTableModel(JTable table) {
    114         return (HistoryBrowserModel.RelationMemberTableModel) table.getModel();
     95    protected DiffTableModel getRelationMemberTableModel(JTable table) {
     96        return (DiffTableModel) table.getModel();
    11597    }
    11698}
  • trunk/src/org/openstreetmap/josm/gui/history/RelationMemberListViewer.java

    r5266 r5627  
    55import java.awt.GridBagLayout;
    66import java.awt.Insets;
     7import java.awt.Rectangle;
    78
    89import javax.swing.JPanel;
     
    1011import javax.swing.JTable;
    1112import javax.swing.ListSelectionModel;
     13import javax.swing.event.TableModelEvent;
     14import javax.swing.event.TableModelListener;
     15
     16import org.openstreetmap.josm.data.osm.history.History;
    1217/**
    1318 * RelationMemberListViewer is a UI component which displays the  list of relation members of two
     
    3742    }
    3843
     44    protected class MemberModelChanged implements TableModelListener {
     45        private final JTable table;
     46
     47        protected MemberModelChanged(JTable table) {
     48            this.table = table;
     49        }
     50
     51        @Override
     52        public void tableChanged(TableModelEvent e) {
     53            Rectangle rect = table.getCellRect(((DiffTableModel)e.getSource()).getFirstChange(), 0, true);
     54            table.scrollRectToVisible(rect);
     55        }
     56    }
     57
    3958    protected JTable buildReferenceMemberListTable() {
    4059        JTable table = new JTable(
    4160                model.getRelationMemberTableModel(PointInTimeType.REFERENCE_POINT_IN_TIME),
    4261                new RelationMemberTableColumnModel()
    43         );
     62                );
    4463        table.setName("table.referencememberlisttable");
    4564        table.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
    4665        selectionSynchronizer.participateInSynchronizedSelection(table.getSelectionModel());
     66        table.getModel().addTableModelListener(new MemberModelChanged(table));
    4767        return table;
    4868    }
     
    5272                model.getRelationMemberTableModel(PointInTimeType.CURRENT_POINT_IN_TIME),
    5373                new RelationMemberTableColumnModel()
    54         );
     74                );
    5575        table.setName("table.currentmemberlisttable");
    5676        table.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
    5777        selectionSynchronizer.participateInSynchronizedSelection(table.getSelectionModel());
     78        table.getModel().addTableModelListener(new MemberModelChanged(table));
    5879        return table;
    5980    }
  • trunk/src/org/openstreetmap/josm/gui/history/TwoColumnDiff.java

    r4689 r5627  
    33/// Feel free to move me somewhere else. Maybe a bit specific for josm.tools?
    44
     5import java.awt.Color;
    56import java.util.ArrayList;
    67
     8import org.openstreetmap.josm.gui.history.TwoColumnDiff.Item.DiffItemType;
    79import org.openstreetmap.josm.tools.Diff;
    810
     
    2426class TwoColumnDiff {
    2527    public static class Item {
    26         public static final int INSERTED = 1;
    27         public static final int DELETED = 2;
    28         public static final int CHANGED = 3;
    29         public static final int SAME = 4;
    30         public static final int EMPTY = 5; // value should be null
    31         public Item(int state, Object value) {
     28
     29        public enum DiffItemType {
     30            INSERTED(new Color(0xDD, 0xFF, 0xDD)), DELETED(new Color(255,197,197)), CHANGED(new Color(255,234,213)),
     31            SAME(new Color(234,234,234)), EMPTY(new Color(234,234,234));
     32
     33            private final Color color;
     34            private DiffItemType(Color color) {
     35                this.color = color;
     36            }
     37            public Color getColor() {
     38                return color;
     39            }
     40        }
     41
     42        public Item(DiffItemType state, Object value) {
    3243            this.state = state;
    33             this.value = state == EMPTY ? null : value;
     44            this.value = state == DiffItemType.EMPTY ? null : value;
    3445        }
    3546
    3647        public final Object value;
    37         public final int state;
     48        public final DiffItemType state;
    3849    }
    3950
     
    7283            while(ia < script.line0 && ib < script.line1){
    7384                // System.out.println(" "+a[ia] + "\t "+b[ib]);
    74                 Item cell = new Item(Item.SAME, a[ia]);
     85                Item cell = new Item(DiffItemType.SAME, a[ia]);
    7586                referenceDiff.add(cell);
    7687                currentDiff.add(cell);
     
    8293                if(inserted > 0 && deleted > 0) {
    8394                    // System.out.println("="+a[ia] + "\t="+b[ib]);
    84                     referenceDiff.add(new Item(Item.CHANGED, a[ia++]));
    85                     currentDiff.add(new Item(Item.CHANGED, b[ib++]));
     95                    referenceDiff.add(new Item(DiffItemType.CHANGED, a[ia++]));
     96                    currentDiff.add(new Item(DiffItemType.CHANGED, b[ib++]));
    8697                } else if(inserted > 0) {
    8798                    // System.out.println("\t+" + b[ib]);
    88                     referenceDiff.add(new Item(Item.EMPTY, null));
    89                     currentDiff.add(new Item(Item.INSERTED, b[ib++]));
     99                    referenceDiff.add(new Item(DiffItemType.EMPTY, null));
     100                    currentDiff.add(new Item(DiffItemType.INSERTED, b[ib++]));
    90101                } else if(deleted > 0) {
    91102                    // System.out.println("-"+a[ia]);
    92                     referenceDiff.add(new Item(Item.DELETED, a[ia++]));
    93                     currentDiff.add(new Item(Item.EMPTY, null));
     103                    referenceDiff.add(new Item(DiffItemType.DELETED, a[ia++]));
     104                    currentDiff.add(new Item(DiffItemType.EMPTY, null));
    94105                }
    95106                inserted--;
     
    100111        while(ia < a.length && ib < b.length) {
    101112            // System.out.println((ia < a.length ? " "+a[ia]+"\t" : "\t") + (ib < b.length ? " "+b[ib] : ""));
    102             referenceDiff.add(new Item(Item.SAME, a[ia++]));
    103             currentDiff.add(new Item(Item.SAME, b[ib++]));
     113            referenceDiff.add(new Item(DiffItemType.SAME, a[ia++]));
     114            currentDiff.add(new Item(DiffItemType.SAME, b[ib++]));
    104115        }
    105116    }
Note: See TracChangeset for help on using the changeset viewer.