Index: trunk/src/org/openstreetmap/josm/gui/MainApplication.java
===================================================================
--- trunk/src/org/openstreetmap/josm/gui/MainApplication.java	(revision 7382)
+++ trunk/src/org/openstreetmap/josm/gui/MainApplication.java	(revision 7383)
@@ -60,4 +60,5 @@
 import org.openstreetmap.josm.plugins.PluginInformation;
 import org.openstreetmap.josm.tools.BugReportExceptionHandler;
+import org.openstreetmap.josm.tools.FontsManager;
 import org.openstreetmap.josm.tools.I18n;
 import org.openstreetmap.josm.tools.ImageProvider;
@@ -346,4 +347,6 @@
         Main.pref.updateSystemProperties();
 
+        FontsManager.initialize();
+        
         final JFrame mainFrame = new JFrame(tr("Java OpenStreetMap Editor"));
         Main.parent = mainFrame;
Index: trunk/src/org/openstreetmap/josm/gui/mappaint/AreaElemStyle.java
===================================================================
--- trunk/src/org/openstreetmap/josm/gui/mappaint/AreaElemStyle.java	(revision 7382)
+++ trunk/src/org/openstreetmap/josm/gui/mappaint/AreaElemStyle.java	(revision 7383)
@@ -34,5 +34,6 @@
     }
 
-    public static AreaElemStyle create(Cascade c) {
+    public static AreaElemStyle create(final Environment env) {
+        final Cascade c = env.mc.getCascade(env.layer);
         MapImage fillImage = null;
         Color color = null;
@@ -75,5 +76,5 @@
         Keyword textPos = c.get(TEXT_POSITION, null, Keyword.class);
         if (textPos == null || "center".equals(textPos.val)) {
-            text = TextElement.create(c, PaintColors.AREA_TEXT.get(), true);
+            text = TextElement.create(env, PaintColors.AREA_TEXT.get(), true);
         }
 
Index: trunk/src/org/openstreetmap/josm/gui/mappaint/BoxTextElemStyle.java
===================================================================
--- trunk/src/org/openstreetmap/josm/gui/mappaint/BoxTextElemStyle.java	(revision 7382)
+++ trunk/src/org/openstreetmap/josm/gui/mappaint/BoxTextElemStyle.java	(revision 7383)
@@ -111,5 +111,5 @@
         Cascade c = env.mc.getCascade(env.layer);
 
-        TextElement text = TextElement.create(c, DEFAULT_TEXT_COLOR, false);
+        TextElement text = TextElement.create(env, DEFAULT_TEXT_COLOR, false);
         if (text == null) return null;
         // Skip any primitives that don't have text to draw. (Styles are recreated for any tag change.)
Index: trunk/src/org/openstreetmap/josm/gui/mappaint/ElemStyle.java
===================================================================
--- trunk/src/org/openstreetmap/josm/gui/mappaint/ElemStyle.java	(revision 7382)
+++ trunk/src/org/openstreetmap/josm/gui/mappaint/ElemStyle.java	(revision 7383)
@@ -112,5 +112,5 @@
                 n = DEFAULT_FONT_NAME;
                 if (n == null) {
-                    DEFAULT_FONT_NAME = n = Main.pref.get("mappaint.font", "Helvetica");
+                    DEFAULT_FONT_NAME = n = Main.pref.get("mappaint.font", "Droid Sans");
                 }
             }
@@ -174,5 +174,5 @@
     }
 
-    protected static Font getFont(Cascade c) {
+    protected static Font getFont(Cascade c, String s) {
         String name = c.get("font-family", getDefaultFontName(), String.class);
         float size = c.get("font-size", getDefaultFontSize(), Float.class);
@@ -185,5 +185,12 @@
             style = Font.ITALIC;
         }
-        return getCachedFont(name, style | weight, Math.round(size));
+        Font f = getCachedFont(name, style | weight, Math.round(size));
+        if (f.canDisplayUpTo(s) == -1)
+            return f;
+        else {
+            // fallback if the string contains characters that cannot be
+            // rendered by the selected font
+            return getCachedFont("SansSerif", style | weight, Math.round(size));
+        }
     }
 
Index: trunk/src/org/openstreetmap/josm/gui/mappaint/ElemStyles.java
===================================================================
--- trunk/src/org/openstreetmap/josm/gui/mappaint/ElemStyles.java	(revision 7382)
+++ trunk/src/org/openstreetmap/josm/gui/mappaint/ElemStyles.java	(revision 7383)
@@ -337,5 +337,5 @@
             Cascade c = e.getValue();
             if (osm instanceof Way) {
-                addIfNotNull(sl, AreaElemStyle.create(c));
+                addIfNotNull(sl, AreaElemStyle.create(env));
                 addIfNotNull(sl, RepeatImageElemStyle.create(env));
                 addIfNotNull(sl, LineElemStyle.createLine(env));
@@ -354,5 +354,5 @@
             } else if (osm instanceof Relation) {
                 if (((Relation)osm).isMultipolygon()) {
-                    addIfNotNull(sl, AreaElemStyle.create(c));
+                    addIfNotNull(sl, AreaElemStyle.create(env));
                     addIfNotNull(sl, RepeatImageElemStyle.create(env));
                     addIfNotNull(sl, LineElemStyle.createLine(env));
Index: trunk/src/org/openstreetmap/josm/gui/mappaint/LineTextElemStyle.java
===================================================================
--- trunk/src/org/openstreetmap/josm/gui/mappaint/LineTextElemStyle.java	(revision 7382)
+++ trunk/src/org/openstreetmap/josm/gui/mappaint/LineTextElemStyle.java	(revision 7383)
@@ -18,6 +18,6 @@
         this.text = text;
     }
-    public static LineTextElemStyle create(Environment env) {
-        Cascade c = env.mc.getCascade(env.layer);
+    public static LineTextElemStyle create(final Environment env) {
+        final Cascade c = env.mc.getCascade(env.layer);
 
         Keyword textPos = c.get(TEXT_POSITION, null, Keyword.class);
@@ -25,5 +25,5 @@
             return null;
 
-        TextElement text = TextElement.create(c, PaintColors.TEXT.get(), false);
+        TextElement text = TextElement.create(env, PaintColors.TEXT.get(), false);
         if (text == null)
             return null;
Index: trunk/src/org/openstreetmap/josm/gui/mappaint/TextElement.java
===================================================================
--- trunk/src/org/openstreetmap/josm/gui/mappaint/TextElement.java	(revision 7382)
+++ trunk/src/org/openstreetmap/josm/gui/mappaint/TextElement.java	(revision 7383)
@@ -116,10 +116,13 @@
      * @throws IllegalArgumentException thrown if {@code defaultTextColor} is null
      */
-    public static TextElement create(Cascade c, Color defaultTextColor, boolean defaultAnnotate)  throws IllegalArgumentException{
+    public static TextElement create(Environment env, Color defaultTextColor, boolean defaultAnnotate)  throws IllegalArgumentException{
         CheckParameterUtil.ensureParameterNotNull(defaultTextColor);
+        Cascade c = env.mc.getCascade(env.layer);
 
         LabelCompositionStrategy strategy = buildLabelCompositionStrategy(c, defaultAnnotate);
         if (strategy == null) return null;
-        Font font = ElemStyle.getFont(c);
+        String s = strategy.compose(env.osm);
+        if (s == null) return null;
+        Font font = ElemStyle.getFont(c, s);
 
         float xOffset = 0;
Index: trunk/src/org/openstreetmap/josm/tools/FontsManager.java
===================================================================
--- trunk/src/org/openstreetmap/josm/tools/FontsManager.java	(revision 7383)
+++ trunk/src/org/openstreetmap/josm/tools/FontsManager.java	(revision 7383)
@@ -0,0 +1,38 @@
+// License: GPL. For details, see LICENSE file.
+package org.openstreetmap.josm.tools;
+
+import java.awt.Font;
+import java.awt.FontFormatException;
+import java.awt.GraphicsEnvironment;
+import java.io.IOException;
+import java.io.InputStream;
+import java.util.Arrays;
+import java.util.Collection;
+import java.util.Map;
+import org.openstreetmap.josm.io.CachedFile;
+
+public class FontsManager {
+
+    public static Map<String, Font> fonts;
+    public static Collection<String> includedFonts = Arrays.asList(
+            "DroidSans.ttf",
+            "DroidSans-Bold.ttf"
+    );
+    
+    public static void initialize() {
+        GraphicsEnvironment ge = GraphicsEnvironment.getLocalGraphicsEnvironment();
+        for (String fontFile : includedFonts) {
+            String url = "resource://data/fonts/"+fontFile;
+            try (InputStream i = new CachedFile(url).getInputStream())
+            {
+                Font f = Font.createFont(Font.TRUETYPE_FONT, i);
+                if (f == null) {
+                    throw new RuntimeException("unable to load font: "+fontFile);
+                }
+                ge.registerFont(f);
+            } catch (IOException | FontFormatException ex) {
+                throw new RuntimeException(ex);
+            }
+        }
+    }
+}
Index: trunk/styles/standard/elemstyles.mapcss
===================================================================
--- trunk/styles/standard/elemstyles.mapcss	(revision 7382)
+++ trunk/styles/standard/elemstyles.mapcss	(revision 7383)
@@ -272,7 +272,4 @@
 node[maxlength] {
     icon-image: "vehicle/restriction/maxlength.png";
-}
-node[maxspeed] {
-    icon-image: "vehicle/restriction/speed.png";
 }
 node[minspeed] {
@@ -3546,4 +3543,65 @@
 }
 
+/******************/
+/* maxspeed nodes */
+/******************/
+node[maxspeed=none] {
+    icon-image: "vehicle/restriction/maxspeed_none.svg";
+}
+node[maxspeed=~/^[0-9]+$/] {
+    maxspeedprop: tag(maxspeed);
+    set maxspeedclass;
+}
+node[maxspeed=signals] {
+    maxspeedprop: " ?";
+    set maxspeedclass;
+}
+node[maxspeed=~/^[0-9]+ mph/] {
+    maxspeedprop: get(split(" mph",tag(maxspeed)),0);
+    set maxspeedclass;
+}
+node[maxspeed=~/[0-9]+ km\/h/] {
+    maxspeedprop: get(split(" km/h",tag(maxspeed)),0);
+    set maxspeedclass;
+}
+node[maxspeed=~/[0-9]+ knots/] {
+    maxspeedprop: get(split(" knots",tag(maxspeed)),0);
+    set maxspeedclass;
+}
+node[prop(maxspeedclass, default)][!is_prop_set(icon-image, default)]::core_maxnodebg {
+    /* background (white) */
+    symbol-shape: circle;
+    symbol-size: 17;
+    symbol-fill-color: white;
+    major-z-index: 4.2;
+}
+node[maxspeed]["maxspeed:variable"]["maxspeed:variable"!="no"][!is_prop_set(icon-image, default)]::core_maxnodebg,
+node[maxspeed=signals][!is_prop_set(icon-image, default)]::core_maxnodebg {
+    /* background (black) */
+    symbol-fill-color: black;
+}
+node[prop(maxspeedclass, default)][!is_prop_set(icon-image, default)]::core_maxnodefg {
+    /* foreground (black text and red circle) */
+    symbol-shape: circle;
+    symbol-size: 15;
+    symbol-stroke-color: crimson;
+    symbol-stroke-width: 2;
+    text: prop(maxspeedprop, default);
+    font-size: 8;
+    font-weight: bold;
+    font-family: "Droid Sans";
+    text-color: black;
+    text-anchor-horizontal: center;
+    text-anchor-vertical: center;
+    text-offset-x: 0;
+    text-offset-y: -1;
+    major-z-index: 4.2;
+}
+node[maxspeed]["maxspeed:variable"]["maxspeed:variable"!="no"][!is_prop_set(icon-image, default)]::core_maxnodefg,
+node[maxspeed=signals][!is_prop_set(icon-image, default)]::core_maxnodefg {
+    /* foreground (white text) */
+    text-color: white;
+}
+
 /***************/
 /* zoom levels */
@@ -3590,7 +3648,6 @@
 }
 
-node|z20,area|z20   { font-size: 9; }
-node|z21,area|z21   { font-size: 10; }
-node|z22-,area|z22- { font-size: 11; }
+node|z19,area|z19   { font-size: 9; }
+node|z20-,area|z20-   { font-size: 10; }
 
 /**************/
