Index: /trunk/src/org/openstreetmap/josm/gui/download/DownloadDialog.java
===================================================================
--- /trunk/src/org/openstreetmap/josm/gui/download/DownloadDialog.java	(revision 12705)
+++ /trunk/src/org/openstreetmap/josm/gui/download/DownloadDialog.java	(revision 12706)
@@ -16,7 +16,7 @@
 import java.awt.event.WindowEvent;
 import java.util.ArrayList;
-import java.util.Arrays;
 import java.util.List;
 import java.util.Optional;
+import java.util.stream.Collectors;
 import java.util.stream.IntStream;
 
@@ -40,4 +40,5 @@
 import org.openstreetmap.josm.data.preferences.BooleanProperty;
 import org.openstreetmap.josm.data.preferences.IntegerProperty;
+import org.openstreetmap.josm.data.preferences.StringProperty;
 import org.openstreetmap.josm.gui.MainApplication;
 import org.openstreetmap.josm.gui.MapView;
@@ -62,5 +63,5 @@
 
     private static final IntegerProperty DOWNLOAD_TAB = new IntegerProperty("download.tab", 0);
-    private static final IntegerProperty DOWNLOAD_SOURCE_TAB = new IntegerProperty("download-source.tab", 0);
+    private static final StringProperty DOWNLOAD_SOURCE_TAB = new StringProperty("download.source.tab", OSMDownloadSource.SIMPLE_NAME);
     private static final BooleanProperty DOWNLOAD_AUTORUN = new BooleanProperty("download.autorun", false);
     private static final BooleanProperty DOWNLOAD_NEWLAYER = new BooleanProperty("download.newlayer", false);
@@ -85,5 +86,5 @@
     protected final transient List<DownloadSelection> downloadSelections = new ArrayList<>();
     protected final JTabbedPane tpDownloadAreaSelectors = new JTabbedPane();
-    protected final JTabbedPane downloadSourcesTab = new JTabbedPane();
+    protected final DownloadSourceTabs downloadSourcesTab = new DownloadSourceTabs();
 
     protected JCheckBox cbNewLayer;
@@ -268,8 +269,6 @@
         }
 
-        for (Component ds : downloadSourcesTab.getComponents()) {
-            if (ds instanceof AbstractDownloadSourcePanel) {
-                ((AbstractDownloadSourcePanel<?>) ds).boudingBoxChanged(b);
-            }
+        for (AbstractDownloadSourcePanel<?> ds : downloadSourcesTab.getAllPanels()) {
+            ds.boudingBoxChanged(b);
         }
     }
@@ -342,7 +341,5 @@
 
         downloadSources.add(downloadSource);
-        if ((ExpertToggleAction.isExpert() && downloadSource.onlyExpert()) || !downloadSource.onlyExpert()) {
-            addNewDownloadSourceTab(downloadSource);
-        }
+        addNewDownloadSourceTab(downloadSource);
     }
 
@@ -362,5 +359,5 @@
     public void rememberSettings() {
         DOWNLOAD_TAB.put(tpDownloadAreaSelectors.getSelectedIndex());
-        DOWNLOAD_SOURCE_TAB.put(downloadSourcesTab.getSelectedIndex());
+        downloadSourcesTab.getSelectedPanel().ifPresent(panel -> DOWNLOAD_SOURCE_TAB.put(panel.getSimpleName()));
         DOWNLOAD_NEWLAYER.put(cbNewLayer.isSelected());
         DOWNLOAD_ZOOMTODATA.put(cbZoomToDownloadedData.isSelected());
@@ -385,10 +382,5 @@
         }
 
-        try {
-            downloadSourcesTab.setSelectedIndex(DOWNLOAD_SOURCE_TAB.get());
-        } catch (IndexOutOfBoundsException e) {
-            Logging.trace(e);
-            downloadSourcesTab.setSelectedIndex(0);
-        }
+        downloadSourcesTab.setSelected(DOWNLOAD_SOURCE_TAB.get());
 
         if (MainApplication.isDisplayingMapView()) {
@@ -483,19 +475,4 @@
 
     /**
-     * Returns position of the download source in the tabbed pane.
-     * @param downloadSource The download source.
-     * @return The index of the download source, or -1 if it not in the pane.
-     */
-    protected int getDownloadSourceIndex(DownloadSource<?> downloadSource) {
-        return Arrays.stream(downloadSourcesTab.getComponents())
-                .filter(it -> it instanceof AbstractDownloadSourcePanel)
-                .map(it -> (AbstractDownloadSourcePanel<?>) it)
-                .filter(it -> it.getDownloadSource().equals(downloadSource))
-                .findAny()
-                .map(downloadSourcesTab::indexOfComponent)
-                .orElse(-1);
-    }
-
-    /**
      * Adds the download source to the download sources tab.
      * @param downloadSource The download source to be added.
@@ -503,13 +480,5 @@
      */
     protected <T> void addNewDownloadSourceTab(DownloadSource<T> downloadSource) {
-        AbstractDownloadSourcePanel<T> panel = downloadSource.createPanel();
-        downloadSourcesTab.add(panel, downloadSource.getLabel());
-        Icon icon = panel.getIcon();
-        if (icon != null) {
-            int idx = getDownloadSourceIndex(downloadSource);
-            downloadSourcesTab.setIconAt(
-                    idx != -1 ? idx : downloadSourcesTab.getTabCount() - 1,
-                    icon);
-        }
+        downloadSourcesTab.addPanel(downloadSource.createPanel());
     }
 
@@ -520,19 +489,5 @@
      */
     private ExpertToggleAction.ExpertModeChangeListener getExpertModeListenerForDownloadSources() {
-        return isExpert -> {
-            if (isExpert) {
-                downloadSources.stream()
-                        .filter(DownloadSource::onlyExpert)
-                        .filter(it -> getDownloadSourceIndex(it) == -1)
-                        .forEach(this::addNewDownloadSourceTab);
-            } else {
-                IntStream.range(0, downloadSourcesTab.getTabCount())
-                        .mapToObj(downloadSourcesTab::getComponentAt)
-                        .filter(it -> it instanceof AbstractDownloadSourcePanel)
-                        .map(it -> (AbstractDownloadSourcePanel<?>) it)
-                        .filter(it -> it.getDownloadSource().onlyExpert())
-                        .forEach(downloadSourcesTab::remove);
-            }
-        };
+        return downloadSourcesTab::updateExpert;
     }
 
@@ -544,12 +499,6 @@
      */
     private ChangeListener getDownloadSourceTabChangeListener() {
-        return ec -> {
-            JTabbedPane tabbedPane = (JTabbedPane) ec.getSource();
-            Component selectedComponent = tabbedPane.getSelectedComponent();
-            if (selectedComponent instanceof AbstractDownloadSourcePanel) {
-                AbstractDownloadSourcePanel<?> panel = (AbstractDownloadSourcePanel<?>) selectedComponent;
-                dialogSplit.setPolicy(panel.getSizingPolicy());
-            }
-        };
+        return ec -> downloadSourcesTab.getSelectedPanel().ifPresent(
+                panel -> dialogSplit.setPolicy(panel.getSizingPolicy()));
     }
 
@@ -568,4 +517,5 @@
          */
         public void run() {
+            rememberSettings();
             setCanceled(true);
             setVisible(false);
@@ -574,12 +524,7 @@
         @Override
         public void actionPerformed(ActionEvent e) {
-            Component panel = downloadSourcesTab.getSelectedComponent();
-            if (panel instanceof AbstractDownloadSourcePanel) {
-                AbstractDownloadSourcePanel<?> pnl = (AbstractDownloadSourcePanel<?>) panel;
-                run();
-                pnl.checkCancel();
-            } else {
-                run();
-            }
+            Optional<AbstractDownloadSourcePanel<?>> panel = downloadSourcesTab.getSelectedPanel();
+            run();
+            panel.ifPresent(AbstractDownloadSourcePanel::checkCancel);
         }
     }
@@ -601,15 +546,13 @@
          */
         public void run() {
-            Component panel = downloadSourcesTab.getSelectedComponent();
-            if (panel instanceof AbstractDownloadSourcePanel) {
-                AbstractDownloadSourcePanel<?> pnl = (AbstractDownloadSourcePanel<?>) panel;
+            rememberSettings();
+            downloadSourcesTab.getSelectedPanel().ifPresent(panel -> {
                 DownloadSettings downloadSettings = getDownloadSettings();
-                if (pnl.checkDownload(downloadSettings)) {
-                    rememberSettings();
+                if (panel.checkDownload(downloadSettings)) {
                     setCanceled(false);
                     setVisible(false);
-                    pnl.triggerDownload(downloadSettings);
+                    panel.triggerDownload(downloadSettings);
                 }
-            }
+            });
         }
 
@@ -629,4 +572,62 @@
         public void windowActivated(WindowEvent e) {
             btnDownload.requestFocusInWindow();
+        }
+    }
+
+    /**
+     * A special tabbed pane for {@link AbstractDownloadSourcePanel}s
+     * @author Michael Zangl
+     * @since 12706
+     */
+    private static class DownloadSourceTabs extends JTabbedPane {
+        private final List<AbstractDownloadSourcePanel<?>> allPanels = new ArrayList<>();
+
+        List<AbstractDownloadSourcePanel<?>> getAllPanels() {
+            return allPanels;
+        }
+
+        List<AbstractDownloadSourcePanel<?>> getVisiblePanels() {
+            return IntStream.range(0, getTabCount())
+                    .mapToObj(this::getComponentAt)
+                    .map(p -> (AbstractDownloadSourcePanel<?>) p)
+                    .collect(Collectors.toList());
+        }
+
+        void setSelected(String simpleName) {
+            getVisiblePanels().stream()
+                .filter(panel -> simpleName.equals(panel.getSimpleName()))
+                .findFirst()
+                .ifPresent(this::setSelectedComponent);
+        }
+
+        void updateExpert(boolean isExpert) {
+            updateTabs();
+        }
+
+        void addPanel(AbstractDownloadSourcePanel<?> panel) {
+            allPanels.add(panel);
+            updateTabs();
+        }
+
+        private void updateTabs() {
+            // Not the best performance, but we don't do it often
+            removeAll();
+
+            boolean isExpert = ExpertToggleAction.isExpert();
+            allPanels.stream()
+                .filter(panel -> isExpert || !panel.getDownloadSource().onlyExpert())
+                .forEach(panel -> addTab(panel.getDownloadSource().getLabel(), panel.getIcon(), panel));
+        }
+
+        Optional<AbstractDownloadSourcePanel<?>> getSelectedPanel() {
+            return Optional.ofNullable((AbstractDownloadSourcePanel<?>) getSelectedComponent());
+        }
+
+        @Override
+        public void insertTab(String title, Icon icon, Component component, String tip, int index) {
+            if (!(component instanceof AbstractDownloadSourcePanel)) {
+                throw new IllegalArgumentException("Can only add AbstractDownloadSourcePanels");
+            }
+            super.insertTab(title, icon, component, tip, index);
         }
     }
Index: /trunk/src/org/openstreetmap/josm/gui/download/OSMDownloadSource.java
===================================================================
--- /trunk/src/org/openstreetmap/josm/gui/download/OSMDownloadSource.java	(revision 12705)
+++ /trunk/src/org/openstreetmap/josm/gui/download/OSMDownloadSource.java	(revision 12706)
@@ -42,4 +42,9 @@
  */
 public class OSMDownloadSource implements DownloadSource<OSMDownloadSource.OSMDownloadData> {
+    /**
+     * The simple name for the {@link OSMDownloadSourcePanel}
+     * @since 12706
+     */
+    public static final String SIMPLE_NAME = "osmdownloadpanel";
 
     @Override
@@ -134,5 +139,4 @@
         private final JLabel sizeCheck = new JLabel();
 
-        private static final String SIMPLE_NAME = "osmdownloadpanel";
         private static final BooleanProperty DOWNLOAD_OSM = new BooleanProperty("download.osm.data", true);
         private static final BooleanProperty DOWNLOAD_GPS = new BooleanProperty("download.osm.gps", false);
