I just got done doing this for the new version of the SDK.Mine loads tiles from an sqlite database.package com.main.utilinspect;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.RandomAccessFile;
import org.codehaus.jackson.JsonNode;
import org.codehaus.jackson.map.ObjectMapper;
import android.content.Context;
import android.util.Log;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import com.esri.android.map.TiledServiceLayer;
import com.esri.core.geometry.Envelope;
import com.esri.core.geometry.Point;
import com.esri.core.geometry.SpatialReference;
public class OfflineDbTiledLayer extends TiledServiceLayer {
File workingDirectory;
String mapDefinition;
String databaseName;
private SQLiteDatabase database;
File blankImage;
byte[] blankImageBytes;
private final Object lock = new Object();
private static final String TAG = "OfflineTiledLayer";
public OfflineDbTiledLayer(Context paramContext, File workingDirectory, String mapDefinition, String databaseName) {
super("required");
this.workingDirectory = workingDirectory;
this.mapDefinition = mapDefinition;
this.databaseName = databaseName;
String databasePath = workingDirectory.getAbsolutePath() + File.separator + databaseName;
this.database = SQLiteDatabase.openDatabase(databasePath, null, SQLiteDatabase.NO_LOCALIZED_COLLATORS);
this.blankImage = new File(workingDirectory.getAbsolutePath() + File.separator + "blank.png");
RandomAccessFile raFile = null;
try {
raFile = new RandomAccessFile(this.blankImage, "r");
blankImageBytes = new byte[(int) raFile.length()];
raFile.readFully(blankImageBytes);
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
finally {
if(raFile != null) {
try {
raFile.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
try
{
ObjectMapper m = new ObjectMapper();
JsonNode root = m.readTree(new File(workingDirectory.getAbsolutePath() + File.separator + mapDefinition));
JsonNode tileInfo = root.get("tileInfo");
double x = tileInfo.get("origin").get("x").asDouble();
double y = tileInfo.get("origin").get("y").asDouble();
Point origin = new Point(x, y);
int dpi = tileInfo.get("dpi").asInt();
int width = tileInfo.get("rows").asInt();
int height = tileInfo.get("cols").asInt();
JsonNode lods = tileInfo.get("lods");
int levels = lods.size();
double resolutions[] = new double[levels];
double scales[] = new double[levels];
for(int i = 0; i < levels; i++)
{
JsonNode level = lods.get(i);
resolutions = level.get("resolution").asDouble();
scales = level.get("scale").asDouble();
}
int wkid = tileInfo.get("spatialReference").get("wkid").asInt();
JsonNode initialExtent = root.get("initialExtent");
Envelope initialExtentEnvelope = new Envelope(
initialExtent.get("xmin").asDouble(),
initialExtent.get("ymin").asDouble(),
initialExtent.get("xmax").asDouble(),
initialExtent.get("ymax").asDouble()
);
JsonNode fullExtent = root.get("fullExtent");
Envelope fullExtentEnvelope = new Envelope(
fullExtent.get("xmin").asDouble(),
fullExtent.get("ymin").asDouble(),
fullExtent.get("xmax").asDouble(),
fullExtent.get("ymax").asDouble()
);
setDefaultSpatialReference(SpatialReference.create(wkid));
setInitialExtent(initialExtentEnvelope);
setFullExtent(fullExtentEnvelope);
setTileInfo(new TileInfo(origin, scales, resolutions, levels, dpi, width, height));
}
catch(Exception ex){
}
super.initLayer();
return;
}
private void openDatabase(){
if(!database.isOpen()){
String databasePath = workingDirectory.getAbsolutePath() + File.separator + databaseName;
this.database = SQLiteDatabase.openDatabase(databasePath, null, SQLiteDatabase.NO_LOCALIZED_COLLATORS);
}
}
private void closeDatabase(){
if(database.isOpen()){
this.database.close();
}
}
@Override
protected byte[] getTile(int level, int column, int row) throws Exception {
byte[] tileImage;
Log.i(TAG, "getTile");
Log.i(TAG, "getTile - retrieving tile");
synchronized(lock) {
Log.i(TAG, "getTile - entered synchronized block - thread " + Integer.toString(android.os.Process.myTid()));
openDatabase();
// First check to see if the tile exists in the database
Cursor tileCursor = database.rawQuery("SELECT image FROM tiles WHERE level = " + Integer.toString(level) + " AND row = " + Integer.toString(row) + " AND column = " + Integer.toString(column), null);
if(tileCursor != null && tileCursor.getCount() > 0) {
tileCursor.moveToFirst();
tileImage = tileCursor.getBlob(0);
Log.i(TAG, "getTile - tile found, returning image");
}
else {
// The tile does not exist in the database, read the blank placeholder tile and serve it
tileImage = blankImageBytes;
Log.i(TAG, "getTile - tile not found returning blank");
}
tileCursor.close();
//this.database.close();
}
Log.i(TAG, "getTile - exited synchronized block");
return tileImage;
}
}