I have successfully integrated my app\'s country search into the global search facility and now I am trying to display each country\'s flag next to the search suggestions.
Sadly after much searching around I have reached the conclusion that you cannot return a uri to an image asset to the search facility. What I did instead was move my flag images to the resources (so they do not clutter up my app's resources I created a library for the flag images) and use resource uri's. So, in my provider I have code that looks like this in the loop that maps database results to search results:
if (requestedColumns[index].compareTo (SearchManager.SUGGEST_COLUMN_ICON_1) == 0) {
// Translate the country code into a flag icon uri
String countryCode = dbResults.getString (
dbResults.getColumnIndexOrThrow (queryMappedColumns[index]));
int flagImageID = FlagLookup.smallFlagResourceID (countryCode);
String flagUriStr = "android.resource://com.lesliesoftware.worldinfo/" + flagImageID;
columnValues.add (flagUriStr);
}
and look up code that looks like this:
static public int smallFlagResourceID (String countryCode) {
if (countryCode == null || countryCode.length () == 0)
return R.drawable.flag_small_none;
if (countryCode.equalsIgnoreCase ("aa"))
return R.drawable.flag_small_aa;
else if (countryCode.equalsIgnoreCase ("ac"))
return R.drawable.flag_small_ac;
else if (countryCode.equalsIgnoreCase ("ae"))
return R.drawable.flag_small_ae;
...
I will just have to make sure I create a test that verifies that all countries that have flags returns the expected results.
Just wanted to add to vidstige's answer: I wanted to serve files that I had downloaded to my temporary cache directory earlier, so I can serve external image thumbnails to the SearchView suggestions from URLs in my search ContentProvider. I used this function instead:
@Override
public AssetFileDescriptor openAssetFile(Uri uri, String mode) throws FileNotFoundException {
String filename = uri.getLastPathSegment();
try {
File file = new File(getContext().getCacheDir(), filename);
// image downloading has to be done in the search results provider, since it's not on the UI thread like this guy.
//downloadAndSaveFile("http://urdomain/urfile.png", filename);
AssetFileDescriptor afd = new AssetFileDescriptor(
ParcelFileDescriptor.open(file, ParcelFileDescriptor.MODE_READ_ONLY | ParcelFileDescriptor.MODE_WORLD_READABLE),
0, AssetFileDescriptor.UNKNOWN_LENGTH);
return afd;
} catch (IOException e) {
throw new FileNotFoundException("No asset found: " + uri);
}
}
You first create an AssetProvider
. We will later create uris that will be handled by this class.
public class AssetsProvider extends ContentProvider {
private AssetManager assetManager;
public static final Uri CONTENT_URI =
Uri.parse("content://com.example.assets");
@Override
public int delete(Uri arg0, String arg1, String[] arg2) { return 0; }
@Override
public String getType(Uri uri) { return null; }
@Override
public Uri insert(Uri uri, ContentValues values) { return null; }
@Override
public boolean onCreate() {
assetManager = getContext().getAssets();
return true;
}
@Override
public Cursor query(Uri uri, String[] projection, String selection, String[] selectionArgs, String sortOrder) { return null; }
@Override
public int update(Uri uri, ContentValues values, String selection, String[] selectionArgs) { return 0; }
@Override
public AssetFileDescriptor openAssetFile(Uri uri, String mode) throws FileNotFoundException {
String path = uri.getPath().substring(1);
try {
AssetFileDescriptor afd = assetManager.openFd(path);
return afd;
} catch (IOException e) {
throw new FileNotFoundException("No asset found: " + uri, e);
}
}
}
Lot's of boilerplate in there. The essential method is of course the openAssetFile
that justs translates the path of the uri passed to it into a AssetFileDescriptor
. In order for Android to be able to pass URIs to this provider, remember to include this in your AndroidManifest.xml file inside the application-tag:
<provider
android:name=".AssetsProvider"
android:authorities="com.example.assets" />
Now, in your search provider you can create an URI like this:
content://com.example.assets/my_folder_inside_assets/myfile.png
I was able to refer images from drawable in SearchRecentSuggestionsProvider using following uri,
"android.resource://your.package.here/drawable/image_name