001// License: GPL. For details, see LICENSE file.
002package org.openstreetmap.josm.gui.history;
003
004import java.awt.GridBagConstraints;
005import java.awt.GridBagLayout;
006import java.awt.Insets;
007
008import javax.swing.JPanel;
009import javax.swing.JScrollPane;
010import javax.swing.JTable;
011
012import org.openstreetmap.josm.gui.util.AdjustmentSynchronizer;
013
014/**
015 * Base class of {@link TagInfoViewer} and {@link RelationMemberListViewer}.
016 * @since 6207
017 */
018public abstract class HistoryViewerPanel extends JPanel {
019    
020    protected HistoryBrowserModel model;
021    protected VersionInfoPanel referenceInfoPanel;
022    protected VersionInfoPanel currentInfoPanel;
023    protected AdjustmentSynchronizer adjustmentSynchronizer;
024    protected SelectionSynchronizer selectionSynchronizer;
025
026    protected HistoryViewerPanel(HistoryBrowserModel model) {
027        setModel(model);
028        build();
029    }
030    
031    private JScrollPane embedInScrollPane(JTable table) {
032        JScrollPane pane = new JScrollPane(table);
033        adjustmentSynchronizer.participateInSynchronizedScrolling(pane.getVerticalScrollBar());
034        return pane;
035    }
036    
037    /**
038     * Sets the history browsing model.
039     * @param model The history browsing model
040     */
041    public final void setModel(HistoryBrowserModel model) {
042        if (this.model != null) {
043            unregisterAsObserver(model);
044        }
045        this.model = model;
046        if (this.model != null) {
047            registerAsObserver(model);
048        }
049    }
050    
051    protected final void unregisterAsObserver(HistoryBrowserModel model) {
052        if (currentInfoPanel != null) {
053            model.deleteObserver(currentInfoPanel);
054        }
055        if (referenceInfoPanel != null) {
056            model.deleteObserver(referenceInfoPanel);
057        }
058    }
059    
060    protected final void registerAsObserver(HistoryBrowserModel model) {
061        if (currentInfoPanel != null) {
062            model.addObserver(currentInfoPanel);
063        }
064        if (referenceInfoPanel != null) {
065            model.addObserver(referenceInfoPanel);
066        }
067    }
068    
069    protected abstract JTable buildReferenceTable();
070    
071    protected abstract JTable buildCurrentTable();
072    
073    private void build() {
074        setLayout(new GridBagLayout());
075        GridBagConstraints gc = new GridBagConstraints();
076
077        // ---------------------------
078        gc.gridx = 0;
079        gc.gridy = 0;
080        gc.gridwidth = 1;
081        gc.gridheight = 1;
082        gc.weightx = 0.5;
083        gc.weighty = 0.0;
084        gc.insets = new Insets(5,5,5,0);
085        gc.fill = GridBagConstraints.HORIZONTAL;
086        gc.anchor = GridBagConstraints.FIRST_LINE_START;
087        referenceInfoPanel = new VersionInfoPanel(model, PointInTimeType.REFERENCE_POINT_IN_TIME);
088        add(referenceInfoPanel,gc);
089
090        gc.gridx = 1;
091        gc.gridy = 0;
092        gc.gridwidth = 1;
093        gc.gridheight = 1;
094        gc.fill = GridBagConstraints.HORIZONTAL;
095        gc.weightx = 0.5;
096        gc.weighty = 0.0;
097        gc.anchor = GridBagConstraints.FIRST_LINE_START;
098        currentInfoPanel = new VersionInfoPanel(model, PointInTimeType.CURRENT_POINT_IN_TIME);
099        add(currentInfoPanel,gc);
100
101        adjustmentSynchronizer = new AdjustmentSynchronizer();
102        selectionSynchronizer = new SelectionSynchronizer();
103
104        // ---------------------------
105        gc.gridx = 0;
106        gc.gridy = 1;
107        gc.gridwidth = 1;
108        gc.gridheight = 1;
109        gc.weightx = 0.5;
110        gc.weighty = 1.0;
111        gc.fill = GridBagConstraints.BOTH;
112        gc.anchor = GridBagConstraints.NORTHWEST;
113        add(embedInScrollPane(buildReferenceTable()),gc);
114
115        gc.gridx = 1;
116        gc.gridy = 1;
117        gc.gridwidth = 1;
118        gc.gridheight = 1;
119        gc.weightx = 0.5;
120        gc.weighty = 1.0;
121        gc.fill = GridBagConstraints.BOTH;
122        gc.anchor = GridBagConstraints.NORTHWEST;
123        add(embedInScrollPane(buildCurrentTable()),gc);
124    }
125}