Index: /trunk/data/maps.xsd
===================================================================
--- /trunk/data/maps.xsd	(revision 9133)
+++ /trunk/data/maps.xsd	(revision 9134)
@@ -689,4 +689,8 @@
 								</xs:complexType>
 							</xs:element>
+							<!--  is imagery properly georeferenced (i.e. no need to check offsets). Defaults to false. Affects showing warnings. -->
+							<xs:element name="valid-georeference" minOccurs="0" maxOccurs="1" type="xs:boolean" />
+							<!-- does imagery server supports JOSM 4326 to 3857 reprojection and non-square queries. Affects showing warnings. -->
+							<xs:element name="epsg4326to3857Supported" minOccurs="0" maxOccurs="1" type="xs:boolean" />
 						</xs:choice>
 					</xs:sequence>
Index: /trunk/src/org/openstreetmap/josm/actions/AddImageryLayerAction.java
===================================================================
--- /trunk/src/org/openstreetmap/josm/actions/AddImageryLayerAction.java	(revision 9133)
+++ /trunk/src/org/openstreetmap/josm/actions/AddImageryLayerAction.java	(revision 9134)
@@ -83,5 +83,5 @@
             if (infoToAdd != null) {
                 Main.main.addLayer(ImageryLayer.create(infoToAdd));
-                AlignImageryPanel.addNagPanelIfNeeded();
+                AlignImageryPanel.addNagPanelIfNeeded(infoToAdd);
             }
         } catch (IllegalArgumentException ex) {
Index: /trunk/src/org/openstreetmap/josm/data/imagery/ImageryInfo.java
===================================================================
--- /trunk/src/org/openstreetmap/josm/data/imagery/ImageryInfo.java	(revision 9133)
+++ /trunk/src/org/openstreetmap/josm/data/imagery/ImageryInfo.java	(revision 9134)
@@ -200,5 +200,7 @@
     /** icon used in menu */
     private String icon;
-    // when adding a field, also adapt the ImageryInfo(ImageryInfo) constructor, equals method, and ImageryPreferenceEntry
+    private boolean isGeoreferenceValid = false;
+    private boolean isEpsg4326To3857Supported = false;
+    // when adding a field, also adapt the ImageryInfo(ImageryInfo) and ImageryInfo(ImageryPreferenceEntry) constructor, equals method, and ImageryPreferenceEntry
 
     /**
@@ -230,4 +232,6 @@
         @pref int tileSize = OsmMercator.DEFAUL_TILE_SIZE;
         @pref Map<String, String> metadataHeaders;
+        @pref boolean valid_georeference;
+        @pref boolean supports_epsg_4326_to_3857_conversion;
 
         /**
@@ -292,4 +296,8 @@
 
             tileSize = i.getTileSize();
+
+            valid_georeference = i.isGeoreferenceValid();
+            supports_epsg_4326_to_3857_conversion = i.isEpsg4326To3857Supported();
+
         }
 
@@ -413,4 +421,6 @@
         setTileSize(e.tileSize);
         metadataHeaders = e.metadataHeaders;
+        isEpsg4326To3857Supported = e.supports_epsg_4326_to_3857_conversion;
+        isGeoreferenceValid = e.valid_georeference;
     }
 
@@ -441,4 +451,6 @@
         this.noTileHeaders = i.noTileHeaders;
         this.metadataHeaders = i.metadataHeaders;
+        this.isEpsg4326To3857Supported = i.isEpsg4326To3857Supported;
+        this.isGeoreferenceValid = i.isGeoreferenceValid;
     }
 
@@ -993,3 +1005,20 @@
         this.metadataHeaders = metadataHeaders;
     }
+
+    public boolean isEpsg4326To3857Supported() {
+        return isEpsg4326To3857Supported;
+    }
+
+    public void setEpsg4326To3857Supported(boolean isEpsg4326To3857Supported) {
+        this.isEpsg4326To3857Supported = isEpsg4326To3857Supported;
+    }
+
+    public boolean isGeoreferenceValid() {
+        return isGeoreferenceValid;
+    }
+
+    public void setGeoreferenceValid(boolean isGeoreferenceValid) {
+        this.isGeoreferenceValid = isGeoreferenceValid;
+    }
+
 }
Index: /trunk/src/org/openstreetmap/josm/gui/layer/AlignImageryPanel.java
===================================================================
--- /trunk/src/org/openstreetmap/josm/gui/layer/AlignImageryPanel.java	(revision 9133)
+++ /trunk/src/org/openstreetmap/josm/gui/layer/AlignImageryPanel.java	(revision 9134)
@@ -12,4 +12,5 @@
 
 import javax.swing.JButton;
+import javax.swing.JCheckBox;
 import javax.swing.JLabel;
 import javax.swing.JPanel;
@@ -19,4 +20,6 @@
 
 import org.openstreetmap.josm.Main;
+import org.openstreetmap.josm.data.imagery.ImageryInfo;
+import org.openstreetmap.josm.data.preferences.BooleanProperty;
 import org.openstreetmap.josm.gui.widgets.UrlLabel;
 import org.openstreetmap.josm.tools.GBC;
@@ -29,13 +32,19 @@
  */
 public class AlignImageryPanel extends JPanel {
-    private static final String PREF = "imagery.offsetnagging";
 
-    public AlignImageryPanel(boolean oneLine) {
+    /**
+     * @param oneLine if true, show the nagging message in one line, otherwise - in two lines
+     * @param showAgain show again property
+     * @param infoToAdd imagery info for which the nagging message is shown
+     */
+    public AlignImageryPanel(boolean oneLine, final BooleanProperty showAgain, ImageryInfo infoToAdd) {
         Font font = getFont().deriveFont(Font.PLAIN, 14.0f);
-        JLabel nagLabel = new JLabel(tr("Aerial imagery might be misaligned. Please check its offset using GPS tracks!"));
+        JLabel nagLabel = new JLabel(tr("Aerial imagery \"{0}\" might be misaligned. Please check its offset using GPS tracks!", infoToAdd.getName()));
         UrlLabel detailsList = new UrlLabel(tr("http://wiki.openstreetmap.org/wiki/Using_Imagery"), tr("Details..."));
         nagLabel.setLabelFor(detailsList);
         nagLabel.setFont(font);
         detailsList.setFont(font);
+        final JCheckBox doNotShowAgain = new JCheckBox(tr("Do not show this message again"));
+        doNotShowAgain.setOpaque(false);
 
         JButton closeButton = new JButton(ImageProvider.get("misc", "black_x"));
@@ -49,5 +58,7 @@
                 if (Main.isDisplayingMapView()) {
                     Main.map.removeTopPanel(AlignImageryPanel.class);
-                    Main.pref.put(PREF, false);
+                    if (doNotShowAgain.isSelected()) {
+                        showAgain.put(false);
+                    }
                 }
             }
@@ -58,8 +69,10 @@
             add(nagLabel, GBC.std(1, 1).fill());
             add(detailsList, GBC.std(1, 2).fill());
+            add(doNotShowAgain, GBC.std(1, 3).fill());
             add(closeButton, GBC.std(2, 1).span(1, 2).anchor(GBC.EAST));
         } else {
             add(nagLabel, GBC.std(1, 1).fill());
             add(detailsList, GBC.std(2, 1).fill());
+            add(doNotShowAgain, GBC.std(1, 2).fill());
             add(closeButton, GBC.std(3, 1).anchor(GBC.EAST));
         }
@@ -68,9 +81,13 @@
     }
 
-    public static void addNagPanelIfNeeded() {
-        if (Main.isDisplayingMapView() && !Main.pref.getBoolean("expert") && Main.pref.getBoolean(PREF, true)) {
+    /**
+     * @param infoToAdd ImageryInfo for which the nag panel should be created
+     */
+    public static void addNagPanelIfNeeded(ImageryInfo infoToAdd) {
+        BooleanProperty showAgain = new BooleanProperty("message.imagery.nagPanel." + infoToAdd.getUrl(), true);
+        if (Main.isDisplayingMapView() && showAgain.get() && !infoToAdd.isGeoreferenceValid() ) {
             if (Main.map.getTopPanel(AlignImageryPanel.class) == null) {
                 double w = Toolkit.getDefaultToolkit().getScreenSize().getWidth();
-                AlignImageryPanel p = new AlignImageryPanel(w > 1300);
+                AlignImageryPanel p = new AlignImageryPanel(w > 1300, showAgain, infoToAdd);
                 Main.map.addTopPanel(p);
             }
Index: /trunk/src/org/openstreetmap/josm/gui/layer/WMSLayer.java
===================================================================
--- /trunk/src/org/openstreetmap/josm/gui/layer/WMSLayer.java	(revision 9133)
+++ /trunk/src/org/openstreetmap/josm/gui/layer/WMSLayer.java	(revision 9134)
@@ -14,4 +14,5 @@
 import javax.swing.AbstractAction;
 import javax.swing.Action;
+import javax.swing.JOptionPane;
 
 import org.apache.commons.jcs.access.CacheAccess;
@@ -29,4 +30,5 @@
 import org.openstreetmap.josm.data.preferences.IntegerProperty;
 import org.openstreetmap.josm.data.projection.Projection;
+import org.openstreetmap.josm.gui.ExtendedDialog;
 
 /**
@@ -113,5 +115,6 @@
     @Override
     public boolean isProjectionSupported(Projection proj) {
-        return supportedProjections == null || supportedProjections.isEmpty() || supportedProjections.contains(proj.toCode());
+        return supportedProjections == null || supportedProjections.isEmpty() || supportedProjections.contains(proj.toCode()) ||
+                (info.isEpsg4326To3857Supported() && supportedProjections.contains("EPSG:4326") &&  "EPSG:3857".equals(Main.getProjection().toCode()));
     }
 
@@ -124,5 +127,5 @@
         String appendix = "";
 
-        if (supportedProjections.contains("EPSG:4326") &&  "EPSG:3857".equals(Main.getProjection().toCode())) {
+        if (isReprojectionPossible()) {
             appendix = ". " + tr("JOSM will use EPSG:4326 to query the server, but results may vary "
                     + "depending on the WMS server");
@@ -133,5 +136,21 @@
     @Override
     public void projectionChanged(Projection oldValue, Projection newValue) {
-        super.projectionChanged(oldValue, newValue);
+        // do not call super - we need custom warning dialog
+
+        if (!isProjectionSupported(newValue)) {
+            String message = tr("The layer {0} does not support the new projection {1}.\n"
+                    + " Supported projections are: {2}\n"
+                    + "Change the projection again or remove the layer.",
+                    getName(), newValue.toCode(), nameSupportedProjections());
+
+            ExtendedDialog warningDialog = new ExtendedDialog(Main.parent, tr("Warning"), new String[]{tr("OK")}).
+                    setContent(message).
+                    setIcon(JOptionPane.WARNING_MESSAGE);
+
+            if (isReprojectionPossible()) {
+                warningDialog.toggleEnable("imagery.wms.projectionSupportWarnings." + tileSource.getBaseUrl());
+            }
+            warningDialog.showDialog();
+        }
 
         if (!newValue.equals(oldValue) && tileSource instanceof TemplatedWMSTileSource) {
@@ -156,3 +175,7 @@
         return AbstractCachedTileSourceLayer.getCache(CACHE_REGION_NAME);
     }
+
+    private boolean isReprojectionPossible() {
+        return supportedProjections.contains("EPSG:4326") &&  "EPSG:3857".equals(Main.getProjection().toCode());
+    }
 }
Index: /trunk/src/org/openstreetmap/josm/io/imagery/ImageryReader.java
===================================================================
--- /trunk/src/org/openstreetmap/josm/io/imagery/ImageryReader.java	(revision 9133)
+++ /trunk/src/org/openstreetmap/josm/io/imagery/ImageryReader.java	(revision 9134)
@@ -143,4 +143,6 @@
                         "icon",
                         "tile-size",
+                        "validGeoreference",
+                        "epsg4326to3857Supported",
                 }).contains(qName)) {
                     newState = State.ENTRY_ATTRIBUTE;
@@ -324,4 +326,10 @@
                     }
                     break;
+                case "valid-georeference":
+                    entry.setGeoreferenceValid(new Boolean(accumulator.toString()));
+                    break;
+                case "epsg4326to3857Supported":
+                    entry.setEpsg4326To3857Supported(new Boolean(accumulator.toString()));
+                    break;
                 }
                 break;
