OSMDROID - 加载从 mapsforge 下载的 .map 文件
Posted
技术标签:
【中文标题】OSMDROID - 加载从 mapsforge 下载的 .map 文件【英文标题】:OSMDROID - loading .map file downloaded from mapsforge 【发布时间】:2017-08-11 19:55:00 【问题描述】:我正在尝试加载 .map 文件,该文件位于 android studio 的 /assets 文件夹中。 .map 文件是从 mapsforge 下载的 @Override protected void onCreate(Bundle savedInstanceState) super.onCreate(savedInstanceState); setContentView(R.layout.activity_main);
map = (MapView) findViewById(R.id.map);
map.setBuiltInZoomControls(true);
map.setTileSource(TileSourceFactory.MAPNIK);
IMapController controller = map.getController();
GeoPoint point = new GeoPoint(41.2585, 69.2097);
controller.animateTo(point);
controller.setZoom(10);
File f = new File("file:///android_asset/" + "myfile.map");
if (f.exists())
File[] list = f.listFiles();
if (list != null)
for (int i = 0; i < list.length; i++)
if (list[i].isDirectory())
continue;
String name = list[i].getName().toLowerCase();
if (!name.contains("."))
continue; //skip files without an extension
name = name.substring(name.lastIndexOf(".") + 1);
if (name.length() == 0)
continue;
if (ArchiveFileFactory.isFileExtensionRegistered(name))
try
OfflineTileProvider tileProvider = new OfflineTileProvider(new SimpleRegisterReceiver(this),
new File[]list[i]);
map.setTileProvider(tileProvider);
String source = "";
IArchiveFile[] archives = tileProvider.getArchives();
if (archives.length > 0)
Set<String> tileSources = archives[0].getTileSources();
if (!tileSources.isEmpty())
source = tileSources.iterator().next();
map.setTileSource(FileBasedTileSource.getSource(source));
else map.setTileSource(TileSourceFactory.DEFAULT_TILE_SOURCE);
else map.setTileSource(TileSourceFactory.DEFAULT_TILE_SOURCE);
map.invalidate();
return;
catch (Exception ex)
ex.printStackTrace();
Toast.makeText(this, f.getAbsolutePath() + " did not have any files I can open! Try using MOBAC", Toast.LENGTH_SHORT).show();
else
Toast.makeText(this, f.getAbsolutePath() + " dir not found!", Toast.LENGTH_SHORT).show();
未找到错误“myfileDirectory”。
【问题讨论】:
File f = new File("file:///android_asset/" + "myfile.map");
。这不起作用,因为 File 类无法处理资产中的文件。谷歌了解如何从资产中读取文件。
if (f.exists()) File[] list = f.listFiles();
。如果f
是您的 .map 文件,那么您怎么能认为您可以列出文件?您并没有像您所说的那样尝试加载该文件,而是将其视为目录。
我尝试使用 InputStream 从资产中读取,但在这里我需要它是 File 而不是 inputStream,我应该在读取后将 inputStream 转换为 File 吗?
您不能将 InputStream 转换为 FIle 对象。你没有对我所说的文件打开和目录列表做出反应。而且您还没有告诉您为什么需要 File 对象。很不清楚你想要你的代码是什么。请先写一篇像样的文章。
我需要在地图视图中打开从mapsforge下载的单个.map文件,如果你不知道怎么做,那么判断我的帖子没有意义
【参考方案1】:
自从我编写了您发布的代码以来,我认为我可以加入。
-
您发布的代码实际上是用于加载 osmdroid 使用默认切片提供程序链(sqlite、mbtile、zip 等)支持的离线切片数据库集合。 Mapsforge 不在该列表中,因为它是一种特殊情况。
要在 osmdroid 中使用 maps forge 提供的图块,您可能应该遵循此示例 https://github.com/osmdroid/osmdroid/blob/master/OpenStreetMapViewer/src/main/java/org/osmdroid/samplefragments/tileproviders/MapsforgeTileProviderSample.java 我相信您会在此处提供各种其他有用的示例。
在资产文件夹中捆绑地图文件或任何其他数据库(尽管可以这样做)在 osmdroid 中加载此图块是不可能的,除非将原始 jpg/png 存储在资产中。因此,如果捆绑资产是您选择的路径,您需要将数据库复制到设备存储,然后告诉 osmdroid 加载它。我不知道为什么,但这可能与权限有关。
为了节省您一些时间,这里是相关的 sn-p 代码,其中 maps
是 File[]
。
XmlRenderTheme theme = null;
try
theme = new AssetsRenderTheme(getContext().getApplicationContext(), "renderthemes/", "rendertheme-v4.xml");
catch (Exception ex)
ex.printStackTrace();
fromFiles = MapsForgeTileSource.createFromFiles(maps, theme, "rendertheme-v4");
forge = new MapsForgeTileProvider(
new SimpleRegisterReceiver(getContext()),
fromFiles, null);
mMapView.setTileProvider(forge);
【讨论】:
非常感谢,我会检查【参考方案2】:回答我自己的问题, *.map文件需要放在/sdcard/osmdroid/下
感谢http://programtalk.com/java-api-usage-examples/org.osmdroid.mapsforge.MapsForgeTileProvider/
在 OnCreate 内 ...
mMap = (MapView) findViewById(R.id.map);
Set<File> mapfiles = findMapFiles();
File[] maps = new File[mapfiles.size()];
maps = mapfiles.toArray(maps);
if (maps.length==0)Log.d(TAG, "No Mapsforge files found");
else Toast.makeText(this, "Loaded " + maps.length + " map files",
Toast.LENGTH_LONG).show();
XmlRenderTheme theme = null;
try
theme = new AssetsRenderTheme(getApplicationContext(),
"renderthemes/","rendertheme-v4.xml");
catch (Exception ex)
ex.printStackTrace();
MapsForgeTileProvider forge = new MapsForgeTileProvider(new
SimpleRegisterReceiver(this), MapsForgeTileSource.createFromFiles(maps,
theme, "rendertheme-v4"), null);
mMap.setTileProvider(forge);
mMap.setUseDataConnection(false);
mMap.setMultiTouchControls(true);
mMap.setBuiltInZoomControls(true);
获取.map文件的方法
protected static Set<File> findMapFiles()
Set<File> maps = new HashSet<>();
List<StorageUtils.StorageInfo> storageList =
StorageUtils.getStorageList();
for (int i = 0; i < storageList.size(); i++)
File f = new File(storageList.get(i).path + File.separator +
"osmdroid" + File.separator);
if (f.exists())
maps.addAll(scan(f));
return maps;
static private Collection<? extends File> scan(File f)
List<File> ret = new ArrayList<>();
File[] files = f.listFiles(new FileFilter()
@Override
public boolean accept(File pathname)
if (pathname.getName().toLowerCase().endsWith(".map"))
return true;
return false;
);
if (files != null)
for (int i = 0; i < files.length; i++)
ret.add(files[i]);
return ret;
【讨论】:
【参考方案3】:如果OfflineTileProvider
无法从InputStream
读取,但需要File
对象到.map 文件,那么您应该首先关注真实文件。
因此,首先将资产中的所有“文件”复制到文件系统上的文件中。
之后你就可以使用这些文件了。
将文件从资产复制到文件存储的代码已在此处发布了一百次。
【讨论】:
只有一个 .map 文件 答案对一个文件也有效。你想说什么?以上是关于OSMDROID - 加载从 mapsforge 下载的 .map 文件的主要内容,如果未能解决你的问题,请参考以下文章
Osmdroid:如何从我自己的位图(图块)创建和加载地图?