简体   繁体   English

Java:使用在线位图图块而不是离线渲染器时缩放 Mapsforge 地图

[英]Java: Scale Mapsforge Map when using online bitmap tiles instead of offline renderer

I use MapsForge 0.8 to display maps in my Android app.我使用MapsForge 0.8在我的 Android 应用程序中显示地图。 When using online tiles (which are just bitmaps and not vector data that can be adjusted in the runtime renderer), the map is really tiny on my Hi-resolution device and I can't read anything.当使用在线图块(它只是位图而不是可以在运行时渲染器中调整的矢量数据)时,我的高分辨率设备上的地图非常小,我无法读取任何内容。

截屏

I would like to scale the map and I have tried the following:我想缩放地图,我尝试了以下方法:

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

And:和:

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

But it does not change anything.但它不会改变任何东西。
How to make it display the map bigger?如何让它显示更大的地图?

Update:更新:

And I don't mean zooming in. I mean scaling the current zoom level to make it readable on high-resolution devices.我的意思不是放大。我的意思是缩放当前缩放级别以使其在高分辨率设备上可读。 Imagine the screenshot above on a small smartphone - it is tiny.想象一下上面在小型智能手机上的屏幕截图 - 它很小。 I can't even read the street names.我什至看不懂街道名称。

2nd Update第二次更新

The current answers below do NOT answer the question.下面的当前答案不回答问题。 This is about scaling Online tiles which are BITMAPS - and NOT how to influence rendering the vector data.这是关于缩放位图的在线图块 - 而不是如何影响渲染矢量数据。

3rd Update第三次更新

The accepted answer finally solved the issue!接受的答案终于解决了问题!

As per this documentaion ,(Read Specifying the Position section) you can specify area to display and at what zoom level.根据本文档,(阅读指定位置部分)您可以指定要显示的区域和缩放级别。

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

Above solution will work as it is provided in official documentation.上述解决方案将按照官方文档中提供的方式工作。

Apart from this I have also searched regarding this and find out we can also set MapPosition to MapViewPosition like(See this link ).除此之外,我还对此进行了搜索,发现我们还可以将MapPosition设置为MapViewPosition 之类的(请参阅此链接)。

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

Hope this will help you.希望这会帮助你。

There are a lot of ways of 'scaling' in mapsforge.在mapsforge中有很多“缩放”的方法。
As it is shown in this example , you can try to .zoom() the mapViewPosition instead of scaling the Model directly.如本所示,您可以尝试.zoom() mapViewPosition而不是直接缩放模型。
If that is what you're asking for, try the following:如果这就是您的要求,请尝试以下操作:

Code:代码:

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

I can't even read the street names.我什至看不懂街道名称。

But if you are talking about the UI TEXT instead, you can try to change it like this:但是如果你是在谈论UI TEXT ,你可以尝试像这样改变它:

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

If only the text size isn't enough for you, you may try creating a new RenderTheme instead.如果仅文本大小对您来说不够,您可以尝试创建一个新的RenderTheme
Docs' Example:文档示例:

Code:代码:

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

XML: 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>

I searched and found this link and this issue (Support resolution-dependent images in render-themes) about the unreadability problem in high resolution devices.我搜索并找到了有关高分辨率设备中的不可读性问题的此链接此问题(在渲染主题中支持分辨率相关的图像) It seem there are two concerns here:这里似乎有两个问题:

Text rendering: How to make text (labels) larger?文本渲染:如何使文本(标签)变大?

Solution for this problem is to use TileRendererLayer.setTextScale(float textScale) :这个问题的解决方案是使用TileRendererLayer.setTextScale(float textScale)

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

Symbols/Icons Rendering:符号/图标渲染:

Ludwig Brinckmann says in second link : Ludwig Brinckmann第二个链接中说:

There is quite a bit of support for this in the Rescue branch through the use of SVG images and tile scaling.通过使用 SVG 图像和平铺缩放,在 Rescue 分支中有相当多的支持。

This is that branch but I think it's already merged to the project.这是那个分支,但我认为它已经合并到项目中。 So it seems for icons, you need to use SVG renderer which according to docs , scale automatically:因此,对于图标,您需要使用 SVG 渲染器,根据docs自动缩放:

SVG Symbols SVG 符号

Symbols can be either defined in the raster PNG format or as vector graphics in SVG format.符号可以定义为光栅 PNG 格式,也可以定义为 SVG 格式的矢量图形。

... ...

SVG Scaling SVG 缩放

SVG resources can now be automatically scaled to accommodate different device resolutions. SVG 资源现在可以自动缩放以适应不同的设备分辨率。

I don't mean zooming in. I mean scaling the current zoom level to make it readable on high-resolution devices.我的意思不是放大。我的意思是缩放当前缩放级别以使其在高分辨率设备上可读。

This is just not a distinction that exists in reality.这并不是现实中存在的区别。

What you're describing is basically a texture, so I will use the word 'texture' instead of 'bitmap'.您所描述的基本上是一种纹理,因此我将使用“纹理”一词而不是“位图”。


At any zoom level, a set amount of screen pixels get mapped to a particular real world area in meters.在任何缩放级别,一定数量的屏幕像素都会以米为单位映射到特定的现实世界区域。 This is your map scale or "zoom level" - the thing in the corner of any map.这是您的地图比例或“缩放级别”——任何地图角落的东西。 For example, 10 pixels = 1km.例如,10 个像素 = 1km。

Your image has an area which it represents, say a 1km square in London, and a size in pixels, say 40x40.您的图像有一个区域,例如伦敦的 1 平方公里,以及以像素为单位的大小,例如 40x40。

When the software tries to draw your texture to the screen it needs to map the pixels of your texture to screen pixels.当软件尝试将您的纹理绘制到屏幕时,它需要将您的纹理像素映射到屏幕像素。 In our example, our zoom level is 10 pixels = 1km, so a 1km square on screen is 10x10 pixels.在我们的示例中,我们的缩放级别是 10 像素 = 1 公里,因此屏幕上 1 公里的正方形是 10x10 像素。 Our texture also represents a 1km square but has more pixels (40x40).我们的纹理也代表了一个 1km 的正方形,但有更多的像素 (40x40)。

Because these values are different, we need to somehow make our texture smaller.因为这些值不同,我们需要以某种方式使我们的纹理更小。 This is called texture filtering , and can also be done to make a texture larger.这称为纹理过滤,也可以使纹理更大。

The reason your texture looks bad on a high-resolution device is down to how the filtering is behaving.您的纹理在高分辨率设备上看起来很糟糕的原因在于过滤的行为方式。 You may be able to achieve acceptable results if you use some kind of mipmap , reducing the level of detail as the user zooms out.如果您使用某种mipmap ,您可能能够获得可接受的结果,随着用户缩小而降低细节级别。 This would be analogous to how Google maps removes labels as you get further out.这类似于谷歌地图在您越走越远时删除标签的方式。


You will never be able to see a high level of detail from a high zoom level.您将永远无法从高缩放级别看到高级别的细节。 That's why the answer saying "just zoom in!"这就是为什么答案说“放大!” are technically right.在技​​术上是正确的。

If you simply increase the area the texture applies to without equally scaling (zooming) the map, your texture and underlying map will get out of sync and that's definitely not desirable.如果您只是增加纹理适用的区域,而没有对贴图进行同等缩放(缩放),您的贴图和底层贴图将不同步,这绝对是不可取的。

Map view tile size is what defines the rendering, both in vector and raster maps.地图视图平铺大小定义了矢量和光栅地图中的渲染。

We have examples with raster tile sources in Mapsforge samples app, eg DownloadLayerViewer.我们在 Mapsforge 示例应用程序中提供了光栅图块源示例,例如 DownloadLayerViewer。 There a fixed tile size 256px is used, as that is provided by the tile source:使用了固定的 tile 大小 256px,这是由 tile 源提供的:

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

If you remove that line, then the map view tile size will be auto-calculated based on device dpi (like in vector maps) and so the raster tiles would appear bigger (though a bit blurry).如果您删除那条线,那么地图视图图块大小将根据设备 dpi 自动计算(如在矢量地图中),因此光栅图块会显得更大(虽然有点模糊)。

Source: MapsForge Google Development Group 来源:MapsForge 谷歌开发组

Removing this line made it work.删除这条线使它工作。 Previously I tried setting the tile size to a different value, but never tried to remove the setting completely.以前我尝试将磁贴大小设置为不同的值,但从未尝试完全删除设置。

JUST........ZOOM......... IN!!!!!!!!!只是……放大……放大!!!!!!!!! Also, try setting this:另外,尝试设置:

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

to this:对此:

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

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 osmdroid-捆绑离线地图磁贴 - osmdroid - Bundle Offline Map Tiles 为JMapViewer创建脱机地图图块 - Creating offline map tiles for JMapViewer 使用地图启动2个或更多活动时,Android Mapsforge内存不足 - Android Mapsforge out of memory when starting 2 or more activities with map 展开地图库:从提供者处获取地图图块以供离线使用 - unfolding map library: get map tiles from provider for offline use 如何从 OpenStreetMap 离线创建地图图块,并在 Android 上显示? - How to create map tiles from OpenStreetMap offline, display it on Android? 如何使离线 Java 应用程序在线可用? - How to make an offline java application available online? Java / adobe air中的脱机在线应用程序体系结构 - offline online application architecture in java/adobe air 当 kafka 生产者在线或离线时获取通知 - get notifications when kafka producer is online or offline 如何在java中将8位灰度位图转换为4位? - how to convert a 8 bit gray scale bitmap to 4 bit scale in java? 没有使用Firebase的互联网连接时如何获取对手用户的在线/离线状态 - How to get online/offline state of the opponent user when there is no internet connection using firebase
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM