Ticket #12644: patch-map-view-scale.patch

File patch-map-view-scale.patch, 7.8 KB (added by michael2402, 8 years ago)
  • src/org/openstreetmap/josm/gui/MapScaler.java

    diff --git a/src/org/openstreetmap/josm/gui/MapScaler.java b/src/org/openstreetmap/josm/gui/MapScaler.java
    index ddb6f84..afa2a6e 100644
    a b import static org.openstreetmap.josm.gui.help.HelpUtil.ht;  
    55import static org.openstreetmap.josm.tools.I18n.marktr;
    66
    77import java.awt.Color;
     8import java.awt.Dimension;
    89import java.awt.Graphics;
    910import java.awt.geom.Rectangle2D;
    1011
    public class MapScaler extends JComponent implements Helpful, Accessible {  
    2425
    2526    private final NavigatableComponent mv;
    2627
    27     private static final int PADDING_RIGHT = 100;
     28    private final static int PADDING_LEFT = 5;
     29    private final static int PADDING_RIGHT = 50;
    2830
    2931    /**
    3032     * Constructs a new {@code MapScaler}.
    public class MapScaler extends JComponent implements Helpful, Accessible {  
    3234     */
    3335    public MapScaler(NavigatableComponent mv) {
    3436        this.mv = mv;
    35         setSize(100+PADDING_RIGHT, 30);
     37        setPreferredLineLength(100);
    3638        setOpaque(false);
    3739    }
    3840
     41    /**
     42     * Sets the preferred length the distance line should have.
     43     * @param pixel The length.
     44     */
     45    public void setPreferredLineLength(int pixel) {
     46        setPreferredSize(new Dimension(pixel + PADDING_LEFT + PADDING_RIGHT, 30));
     47    }
     48
    3949    @Override
    4050    public void paint(Graphics g) {
    41         String text = mv.getDist100PixelText();
    42         Rectangle2D bound = g.getFontMetrics().getStringBounds(text, g);
    4351        g.setColor(getColor());
    44         g.drawLine(0, 5, 99, 5);
    45         g.drawLine(0, 0, 0, 10);
    46         g.drawLine(99, 0, 99, 10);
    47         g.drawLine(49, 3, 49, 7);
    48         g.drawLine(24, 3, 24, 7);
    49         g.drawLine(74, 3, 74, 7);
    50         g.drawString(text, (int) (100-bound.getWidth()/2), 23);
    51         g.drawString("0", 0, 23);
     52
     53        double dist100Pixel = mv.getDist100Pixel(true);
     54        TickMarks tickMarks = new TickMarks(dist100Pixel, getWidth() - PADDING_LEFT - PADDING_RIGHT);
     55        tickMarks.paintTicks(g);
    5256    }
    5357
    5458    /**
    public class MapScaler extends JComponent implements Helpful, Accessible {  
    9498            return null;
    9599        }
    96100    }
     101
     102    /**
     103     * This class finds the best possible tick mark positions.
     104     * <p>
     105     * It will attempt to use steps of 1m, 2.5m, 10m, 25m, ...
     106     */
     107    private static final class TickMarks {
     108
     109        private final double dist100Pixel;
     110        private final double lineDistance;
     111        /**
     112         * Distance in meters between two ticks.
     113         */
     114        private final double spacingMeter;
     115        private final int steps;
     116        private final int majorStepEvery;
     117
     118        /**
     119         * Creates a new tick mark helper.
     120         * @param dist100Pixel The distance of 100 pixel on the map.
     121         * @param width The width of the mark.
     122         */
     123        public TickMarks(double dist100Pixel, int width) {
     124            this.dist100Pixel = dist100Pixel;
     125            lineDistance = dist100Pixel * width / 100;
     126
     127            double log10 = Math.log(lineDistance) / Math.log(10);
     128            double spacingLog10 = Math.pow(10, Math.floor(log10));
     129            if (log10 - Math.floor(log10) < .75) {
     130                spacingMeter = spacingLog10 / 4;
     131                majorStepEvery = 4;
     132            } else {
     133                spacingMeter = spacingLog10;
     134                majorStepEvery = 5;
     135            }
     136            steps = (int) Math.floor(lineDistance / spacingMeter);
     137        }
     138
     139        public void paintTicks(Graphics g) {
     140            double spacingPixel = spacingMeter / (dist100Pixel / 100);
     141            double textBlockedUntil = -1;
     142            for (int step = 0; step <= steps; step++) {
     143                int x = (int) (PADDING_LEFT + spacingPixel * step);
     144                boolean isMajor = step % majorStepEvery == 0;
     145                int paddingY = isMajor ? 0 : 3;
     146                g.drawLine(x, paddingY, x, 10 - paddingY);
     147
     148                if (isMajor || (step == steps && textBlockedUntil < 0)) {
     149                    String text;
     150                    if (step == 0) {
     151                        text = "0";
     152                    } else {
     153                        text = NavigatableComponent.getDistText(spacingMeter * step);
     154                    }
     155                    Rectangle2D bound = g.getFontMetrics().getStringBounds(text, g);
     156                    int left = (int) (x - bound.getWidth() / 2);
     157                    if (textBlockedUntil < left) {
     158                        g.drawString(text, left, 23);
     159                        textBlockedUntil = left + bound.getWidth() + 2;
     160                    }
     161                }
     162            }
     163            g.drawLine(PADDING_LEFT + 0, 5, (int) (PADDING_LEFT + spacingPixel * steps), 5);
     164        }
     165    }
    97166}
  • src/org/openstreetmap/josm/gui/MapSlider.java

    diff --git a/src/org/openstreetmap/josm/gui/MapSlider.java b/src/org/openstreetmap/josm/gui/MapSlider.java
    index f6f2fc1..7a1a787 100644
    a b package org.openstreetmap.josm.gui;  
    33
    44import static org.openstreetmap.josm.gui.help.HelpUtil.ht;
    55
     6import java.awt.Dimension;
    67import java.beans.PropertyChangeEvent;
    78import java.beans.PropertyChangeListener;
    89
    910import javax.swing.JSlider;
     11import javax.swing.UIManager;
    1012import javax.swing.event.ChangeEvent;
    1113import javax.swing.event.ChangeListener;
    1214
    class MapSlider extends JSlider implements PropertyChangeListener, ChangeListene  
    2729        addChangeListener(this);
    2830        // Call this manually once so it gets setup correctly
    2931        propertyChange(null);
     32        int w = UIManager.getDefaults().getInt("Slider.thumbWidth") + 150;
     33        setPreferredSize(new Dimension(w, 27));
    3034    }
    3135
    3236    @Override
  • src/org/openstreetmap/josm/gui/MapView.java

    diff --git a/src/org/openstreetmap/josm/gui/MapView.java b/src/org/openstreetmap/josm/gui/MapView.java
    index f509eac..d360b1b 100644
    a b implements PropertyChangeListener, PreferenceChangedListener, OsmDataLayer.Layer  
    279279        Main.pref.addPreferenceChangeListener(this);
    280280
    281281        addComponentListener(new ComponentAdapter() {
    282             @Override public void componentResized(ComponentEvent e) {
     282            @Override
     283            public void componentResized(ComponentEvent e) {
    283284                removeComponentListener(this);
    284285
    285                 for (JComponent c : getMapNavigationComponents(MapView.this)) {
    286                     MapView.this.add(c);
    287                 }
    288 
    289286                mapMover = new MapMover(MapView.this, contentPane);
    290287            }
    291288        });
    implements PropertyChangeListener, PreferenceChangedListener, OsmDataLayer.Layer  
    316313        if (Shortcut.findShortcut(KeyEvent.VK_TAB, 0) != null) {
    317314            setFocusTraversalKeysEnabled(false);
    318315        }
     316
     317        for (JComponent c : getMapNavigationComponents(MapView.this)) {
     318            add(c);
     319        }
    319320    }
    320321
    321322    /**
    implements PropertyChangeListener, PreferenceChangedListener, OsmDataLayer.Layer  
    325326     */
    326327    public static List<? extends JComponent> getMapNavigationComponents(MapView forMapView) {
    327328        MapSlider zoomSlider = new MapSlider(forMapView);
    328         zoomSlider.setBounds(3, 0, 114, 30);
     329        Dimension size = zoomSlider.getPreferredSize();
     330        zoomSlider.setSize(size);
     331        zoomSlider.setLocation(3, 0);
    329332        zoomSlider.setFocusTraversalKeysEnabled(Shortcut.findShortcut(KeyEvent.VK_TAB, 0) == null);
    330333
    331334        MapScaler scaler = new MapScaler(forMapView);
    332         scaler.setLocation(10, 30);
     335        scaler.setPreferredLineLength(size.width - 10);
     336        scaler.setSize(scaler.getPreferredSize());
     337        scaler.setLocation(3, size.height);
    333338
    334339        return Arrays.asList(zoomSlider, scaler);
    335340    }