Osmdroid - 来自脱机文件夹

时间:2014-04-06 12:53:36

标签: datasource osmdroid

我正在使用OSMdroid在我的应用中显示在线和离线数据。离线数据存储在具有所需结构的.zip文件中。

是否可以将这些离线磁贴存储在目录中(提取的.zip文件具有相同的结构)? 有人可以告诉我,我怎么能做到这一点?

谢谢。

2 个答案:

答案 0 :(得分:2)

对不起在问之前我应该​​多试一试。但是我在这里留下这个问题,有人会发现它很有用。

解决方案:

新的MapTileFileProvider。我称它为MapTileFileFolderProvider,它是一个轻微修改的MapTileFileArchiveProvider。它使用文件夹而不是档案。修改并不完美,它是一个热门的解决方案"需要有经验的Java / Android才能使其正常运行。

从文件夹中加载Tiles的好处:

  • 更快地加载瓷砖(我知道,我不会认识到差异)。
  • 更简单的更新仅关注更改的图块而不是整个地图计划。
  • 应用程序可以在"在线模式下下载磁贴"然后使用下载的Tiles离线。

MapTileFileFolderProvider - 仅修改

public class MapTileFileArchiveProvider扩展MapTileFileStorageProviderBase

public class MapTileFileFolderProvider extends MapTileFileStorageProviderBase {
  private final boolean mSpecificFoldersProvided;
  private final ArrayList<String> mFolders = new ArrayList<String>();
  private final AtomicReference<ITileSource> mTileSource = new AtomicReference<ITileSource>();

  ...
}

public MapTileFileArchiveProvider(...)

public MapTileFileFolderProvider(final IRegisterReceiver pRegisterReceiver,
                               final ITileSource pTileSource, 
                               final String[] pFolders) {
  super(pRegisterReceiver, NUMBER_OF_TILE_FILESYSTEM_THREADS,
                         TILE_FILESYSTEM_MAXIMUM_QUEUE_SIZE);
  setTileSource(pTileSource);
  if (pFolders == null) {
    mSpecificFoldersProvided = false;
    findFolders();
  } else {
    mSpecificFoldersProvided = true;
    for (int i = pFolders.length - 1; i >= 0; i--) {
      mFolders.add(pFolders[i]);
    }
  }
}

findArchiveFiles()

private void findFolders() {
  mFolders.clear();
  if (!getSdCardAvailable()) {
    return;
  }

  String baseDirPath = Environment.getExternalStorageDirectory().toString()+"/ctu_navigator"; // TODO get from Config
  File dir=new File(baseDirPath);
  final File[] files = dir.listFiles();
  if (files != null) {
  String fileName;
    for (File file : files) {
      if (file.isDirectory()) {
        fileName = baseDirPath + '/' + file.getName();
        mFolders.add(fileName);
        Utils.log(PlanTileProviderFactory.class, "Added map source: " + fileName);
      }
    }
  }
}

@Override
protected String getName() {
  return "Folders Provider";
}

@Override
protected String getThreadGroupName() {
  return "folder";
}

protected class TileLoader extends MapTileModuleProviderBase.TileLoader {

  @Override
  public Drawable loadTile(final MapTileRequestState pState) {
    ITileSource tileSource = mTileSource.get();
    if (tileSource == null) {
      return null;
    }

    final MapTile pTile = pState.getMapTile();

    // if there's no sdcard then don't do anything
    if (!getSdCardAvailable()) {
      Utils.log("No sdcard - do nothing for tile: " + pTile);
      return null;
    }

    InputStream inputStream = null;
    try {
      inputStream = getInputStream(pTile, tileSource);
      if (inputStream != null) {
        Utils.log("Use tile from folder: " + pTile);
        final Drawable drawable = tileSource.getDrawable(inputStream);
        return drawable;
      }
    } catch (final Throwable e) {
      Utils.log("Error loading tile");
      Utils.logError(getClass(), (Exception) e);
    } finally {
      if (inputStream != null) {
        StreamUtils.closeStream(inputStream);
      }
    }
    return null;
  }

  private synchronized InputStream getInputStream(final MapTile pTile, final ITileSource tileSource) {
    for (final String folder : mFolders) {
      final String path = folder + '/' + tileSource.getTileRelativeFilenameString(pTile);
      File mapTileFile = new File(path);
      InputStream in = null;
      try {
        in = new BufferedInputStream(new FileInputStream(mapTileFile));
      } catch (IOException e) {
        //Utils.log("Tile " + pTile + " not found in " + path);
      }

      if (in != null) {
        Utils.log("Found tile " + pTile + " in " + path);
        return in;
      }
    }
    Utils.log("Tile " + pTile + " not found.");
    return null;
  }

}

答案 1 :(得分:0)

嗯,据我所知,你想要得到的东西......这或多或少是标准的XYTileSource已经在做的事情。

因此,如果您只是使用像这样的即用型磁贴源:

map.setTileSource(TileSourceFactory.MAPNIK);

你会看到存储在/ sdcard / osmdroid / tiles / Mapnik /

中的下载瓷砖文件

主要区别在于它增加了一个&#34; .tile&#34;每个tile文件末尾的扩展名(可能是为了防止像Android库这样的工具索引所有这些图像)。

如果您有一个可以使用的磁贴的ZIP文件,您可以在此目录中提取它们,并为每个磁贴添加.tile扩展名(355.png =&gt; 355.png.tile)

TileSourceFactory.MAPNIK将能够使用它们。