【问题标题】:Java: Scale Mapsforge Map when using online bitmap tiles instead of offline rendererJava:使用在线位图图块而不是离线渲染器时缩放 Mapsforge 地图
【发布时间】:2017-05-30 00:14:56
【问题描述】:

我使用MapsForge 0.8 在我的 Android 应用中显示地图。当使用在线图块(只是位图而不是可以在运行时渲染器中调整的矢量数据)时,地图在我的高分辨率设备上真的很小,我什么也看不懂。

我想缩放地图并尝试了以下方法:

mapView.getModel().displayModel.setDefaultUserScaleFactor(2.0f);

还有:

mapView.getModel().displayModel.setUserScaleFactor(2.0f);

但它并没有改变任何东西。
如何让它显示地图更大?

更新:

我的意思不是放大。我的意思是缩放当前缩放级别以使其在高分辨率设备上可读。想象一下上面在小型智能手机上的屏幕截图 - 它很小。我什至看不懂街道名称。

第二次更新

以下当前答案不回答问题。这是关于缩放位图的在线图块 - 而不是如何影响矢量数据的渲染。

第三次更新

接受的答案终于解决了问题!

【问题讨论】:

  • 请解释一下您认为“缩放当前缩放级别”与放大有何不同?
  • 如果你读完问题后不明白,那我不知道还有什么要补充的。

标签: java android bitmap scaling mapsforge


【解决方案1】:

地图视图平铺大小是定义渲染的因素,无论是矢量地图还是光栅地图。

我们在 Mapsforge 示例应用程序中提供了光栅图块源示例,例如下载图层查看器。使用了 256px 的固定磁贴大小,由磁贴源提供:

this.mapView.getModel().displayModel.setFixedTileSize(256);

如果您删除该线,则地图视图切片大小将根据设备 dpi 自动计算(如在矢量地图中),因此光栅切片会显得更大(虽然有点模糊)。

Source: MapsForge Google Development Group

删除此行使其工作。以前我尝试将磁贴大小设置为不同的值,但从未尝试完全删除该设置。

【讨论】:

    【解决方案2】:

    我的意思不是放大。我的意思是缩放当前的缩放级别以使 它在高分辨率设备上可读。

    这只是现实中不存在的区别。

    你所描述的基本上是一个纹理,所以我将使用“纹理”这个词而不是“位图”。


    在任何缩放级别,一定数量的屏幕像素都会映射到以米为单位的特定现实世界区域。这是您的地图比例或“缩放级别” - 任何地图角落的东西。例如,10 像素 = 1 公里。

    您的图片有一个区域,例如伦敦 1 公里的正方形,大小以像素为单位,例如 40x40。

    当软件尝试将纹理绘制到屏幕上时,它需要将纹理的像素映射到屏幕像素。在我们的示例中,我们的缩放级别是 10 像素 = 1km,因此屏幕上 1km 的正方形是 10x10 像素。我们的纹理也代表一个 1 公里的正方形,但有更多的像素 (40x40)。

    由于这些值不同,我们需要以某种方式使纹理更小。这称为texture filtering,也可以使纹理变大。

    您的纹理在高分辨率设备上看起来不好的原因在于过滤的行为方式。如果您使用某种mipmap,您可能能够获得可接受的结果,从而在用户缩小时降低细节级别。这类似于 Google 地图在您越走越远时删除标签的方式。


    您将永远无法从高缩放级别看到高层次的细节。这就是为什么答案说“只是放大!”在技​​术上是正确的。

    如果您只是增加纹理应用的区域而不等量缩放(缩放)地图,您的纹理和底层地图将不同步,这绝对是不可取的。

    【讨论】:

    • 在线图块是一张大图。从它的细节来看,这张图片很好。但例如文本太小,我无法在手机上阅读。
    • 是的,所以使用 mipmap 会在这些细节变得不可读时将其删除。
    • 即使我放大到最大并且只有一条街道在我的视野中,我也希望看到街道名称。这是重要的信息。但即便如此,它也会变得难以阅读。
    • 那么你的纹理分辨率不够高。获得更高分辨率的纹理。
    • 哦。我从哪里得到它?
    【解决方案3】:

    我搜索并发现this linkthis issue (Support resolution-dependent images in render-themes) 关于高分辨率设备的不可读性问题。这里似乎有两个问题:

    文字渲染:如何让文字(标签)变大?

    这个问题的解决方法是使用TileRendererLayer.setTextScale(float textScale):

    TileRendererLayer tileRendererLayer = new TileRendererLayer(...);
    mapView.getLayerManager().getLayers().add(tileRendererLayer);
    tileRendererLayer.setTextScale(...)
    

    符号/图标渲染:

    Ludwig Brinckmannsecond link 中说:

    在 Rescue 分支中对此有相当多的支持 SVG 图像和平铺缩放的使用。

    这是that branch,但我认为它已经合并到项目中。所以看起来图标,你需要使用根据docs自动缩放的SVG渲染器:

    SVG 符号

    符号可以定义为光栅 PNG 格式,也可以定义为矢量 SVG 格式的图形。

    ...

    SVG 缩放

    SVG 资源现在可以自动缩放以适应不同的 设备分辨率。

    【讨论】:

    • 当使用渲染器时——在运行时渲染的矢量图形——然后是的。这已经适用于我下载的地图。但是在线图块——只是位图——已经是原样了。我所能做的就是以某种方式缩放图像图块。但不像你描述的那样。还是谢谢。
    【解决方案4】:

    mapsforge 中有很多“缩放”方法。
    正如example 中所示,您可以尝试.zoom() mapViewPosition 而不是直接缩放模型。
    如果这是您的要求,请尝试以下操作:

    代码:

    MapViewPosition mapViewPosition = mapView.getModel().mapViewPosition; 
    mapViewPosition.zoom((byte) XX); // Change it to a number (i.g. "(byte) 3")
    

    我什至看不懂街道名称。

    但如果您是在谈论 UI TEXT,您可以尝试像这样更改它:

    mapView.setTextScale(XX); // Again, number goes here
    

    如果仅文本大小对您来说还不够,您可以尝试创建一个新的RenderTheme
    文档示例:

    代码:

    tileRendererLayer.setXmlRenderTheme(new ExternalRenderTheme(File)) // File should be
                                                     // the XML file for the RenderTheme
    

    XML:

    <?xml version="1.0" encoding="UTF-8"?>
        <rendertheme xmlns="http://mapsforge.org/renderTheme" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://mapsforge.org/renderTheme renderTheme.xsd" version="1">
    
        <!-- matches all ways with a "highway=trunk" or a "highway=motorway" tag -->
        <rule e="way" k="highway" v="trunk|motorway">
            <line stroke="#FF9900" stroke-width="2.5" />
        </rule>
    
        <!-- matches all closed ways (first node equals last node) with an "amenity=…" tag -->
        <rule e="way" k="amenity" v="*" closed="yes">
            <area fill="#DDEECC" stroke="#006699" stroke-width="0.3" />
        </rule>
    
        <!-- matches all nodes with a "tourism=hotel" tag on zoom level 16 and above 
    -->
        <rule e="node" k="tourism" v="hotel" zoom-min="16">
            <symbol src="file:/path/to/symbol/icon/hotel.png" />
            <caption k="name" font-style="bold" font-size="10" fill="#4040ff" />
        </rule>
    </rendertheme>
    

    【讨论】:

    • 当使用渲染器时——在运行时渲染的矢量图形——然后是的。这已经适用于我下载的地图。但是在线图块——只是位图——已经是原样了。我所能做的就是以某种方式缩放图像图块。但不像你描述的那样。还是谢谢。
    【解决方案5】:

    根据documentaion,(阅读指定位置部分)您可以指定要显示的区域和缩放级别。

    this.mapView.setCenter(new LatLong(52.517037, 13.38886));
    this.mapView.setZoomLevel((byte) 12);
    

    上述解决方案将按照官方文档中提供的方式运行。

    除此之外,我还搜索了这个,发现我们还可以将MapPosition 设置为MapViewPosition like(请参阅此link)。

    MapPosition mapPosition1 = new MapPosition(new LatLong(52.517037, 13.38886), (byte) 12);
    this.mapView.getModel().mapViewPosition.setMapPosition(mapPosition1);
    

    希望这会对你有所帮助。

    【讨论】:

    • 很好的答案,但不是我想要的。请查看我的更新。
    • 在你的更新得到你的意思之后.....你需要缩放地图 UI 元素,以便在保持缩放级别的同时可以读取它。
    • 检查这个link。我认为这与您的问题和enhancement 类似。还要检查this
    • 当使用渲染器时——在运行时渲染的矢量图形——然后是的。这已经适用于我下载的地图。但是在线图块——只是位图——已经是原样了。我所能做的就是以某种方式缩放图像图块。但不像你描述的那样。还是谢谢。
    • 是的......我完全同意你的看法......这不是一件简单的事情,需要在现有库中进行大量定制......我刚刚在库中找到了这个方法,所以虽然它会帮助您进行研发。希望你能找到办法。
    【解决方案6】:

    只是............放大............在!!!!!!!!! 另外,请尝试设置:

    mapView.getModel().displayModel.setDefaultUserScaleFactor(2.0f);
    

    到这里:

    mapView.getModel().displayModel.setDefaultUserScaleFactor(3.0f);
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2012-03-27
      • 1970-01-01
      • 1970-01-01
      • 2017-07-28
      • 2017-12-07
      • 1970-01-01
      • 2012-04-19
      • 1970-01-01
      相关资源
      最近更新 更多