/*
* CDDL HEADER START
*
* The contents of this file are subject to the terms of the Common Development
* and Distribution License (the "License").
* You may not use this file except in compliance with the License.
*
* You can obtain a copy of the license at
* src/com/vodafone360/people/VODAFONE.LICENSE.txt or
* http://github.com/360/360-Engine-for-Android
* See the License for the specific language governing permissions and
* limitations under the License.
*
* When distributing Covered Code, include this CDDL HEADER in each file and
* include the License file at src/com/vodafone360/people/VODAFONE.LICENSE.txt.
* If applicable, add the following below this CDDL HEADER, with the fields
* enclosed by brackets "[]" replaced with your own identifying information:
* Portions Copyright [yyyy] [name of copyright owner]
*
* CDDL HEADER END
*
* Copyright 2010 Vodafone Sales & Services Ltd. All rights reserved.
* Use is subject to license terms.
*/
package com.vodafone360.people.utils;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.security.InvalidParameterException;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import com.vodafone360.people.datatypes.ExternalResponseObject;
/**
* Set of static utility functions for handling of thumb-nails within the People
* client. Thumb-nails are stored in a specific sub-directory ('app_np_thumbs')
* of the People application directory. Thumb-nail names are based on a supplied
* ID (local Contact ID).
*/
public final class ThumbnailUtils {
/** Full path for the thumbnails. **/
public static final String THUMBNAIL_FILE_LOCATION = "/data/data/com.vodafone360.people/app_np_thumbs/";
/** JPEG file extension. **/
private static final String JPG_EXTENSION = ".jpg";
/** PNG file extension. **/
public static final String PNG_EXTENSION = ".png";
/** Thumbnail request URI. **/
public static final String REQUEST_THUMBNAIL_URI = "?encoding=png&size=50x50!&wait";
/** Thumbnail file compression quality. **/
private static final int PHOTO_QUALITY = 100;
/** Height of thumb-nails stored by People client. */
private static final int THUMBNAIL_HEIGHT = 50;
/** Width of thumb-nails stored by People client. */
private static final int THUMBNAIL_WIDTH = 50;
/***
* Private constructor to prevent the utility class from being instantiated.
*/
private ThumbnailUtils() {
// Do nothing.
}
/**
* Return path to file containing specified thumb-nail.
*
* @param thumbnailId ID of thumb-nail.
* @return path to thumb-nail file, NULL if it does not exist.
*/
public static String thumbnailPath(final Long thumbnailId) {
if (thumbnailId == null) {
return THUMBNAIL_FILE_LOCATION.substring(0, THUMBNAIL_FILE_LOCATION.length() - 1);
}
/*
* We switched from JPEG to PNG so we have to check both file formats
* for some time. Later only PNG should be checked.
*/
String path = THUMBNAIL_FILE_LOCATION + thumbnailId + PNG_EXTENSION;
if (new File(path).exists()) {
return path;
} else {
path = THUMBNAIL_FILE_LOCATION + thumbnailId + JPG_EXTENSION;
if (new File(path).exists()) {
return path;
}
}
return null;
}
/**
* Generate filename for thumb-nail. This consists of the thumb-nail ID and
* the .JPG extension.
*
* @param thumbnailId ID of thumb-nail (e.g. local Contact ID).
* @return String containing generated filename.
*/
public static String thumbnailFileToWrite(final Long thumbnailId) {
return thumbnailId + PNG_EXTENSION;
}
/**
* Return Bitmap containing thumb-nail matching the supplied ID. A 50 x 50
* Bitmap is generated if a file for the specified ID exists.
*
* @param thumbnailId ID of thumb-nail to retrieve.
* @return Bitmap of the requested thumb-nail, NULL if Bitmap cannot be
* generated.
*/
public static Bitmap thumbnailFromFile(final Long thumbnailId) {
BitmapFactory.Options options = new BitmapFactory.Options();
options.outHeight = THUMBNAIL_HEIGHT;
options.outWidth = THUMBNAIL_WIDTH;
/*
* We switched from JPEG to PNG so we have to check both file formats
* for some time. Later only PNG should be checked.
*/
String path = THUMBNAIL_FILE_LOCATION + thumbnailId + PNG_EXTENSION;
if (!new File(path).exists()) {
path = THUMBNAIL_FILE_LOCATION + thumbnailId + JPG_EXTENSION;
}
return BitmapFactory.decodeFile(path, options);
}
/**
* Checks if the thumbnail folder exists and creates it if not.
*/
private static void ensureThumbnailFolderExists() {
File path = new File(THUMBNAIL_FILE_LOCATION);
if (!path.exists()) {
if (!path.mkdir()) {
LogUtils.logE("ThumbnailUtils.ensureThumbnailFolderExists()");
}
}
}
/***
* Copies and compresses the given bitmap image.
*
* @param destinationPath Path to save new image.
* @param inputPhoto Input Bitmap to save.
* @return TRUE if the photo was successfully saved, FALSE if otherwise.
* @throws IOException Issue with photoPath in the file system.
* @throws FileNotFoundException Issue with photoPath in the file system.
* @throws InvalidParameterException destinationPath is empty.
* @throws InvalidParameterException inputPhoto is NULL.
*/
public static boolean copyAndCompressBitmap(final String destinationPath,
final Bitmap inputPhoto) throws IOException {
if (destinationPath == null || destinationPath.equals("")) {
throw new InvalidParameterException("ThumbnailUtils."
+ "copyAndCompressBitmap() destinationPath cannot be " + "empty");
}
if (inputPhoto == null) {
throw new InvalidParameterException("ThumbnailUtils."
+ "copyAndCompressBitmap() inputPhoto cannot be " + "NULL");
}
ensureThumbnailFolderExists();
/** Create target file. **/
File file = new File(destinationPath);
if (file.exists()) {
if (!file.delete()) {
LogUtils.logE("ThumbnailUtils.copyAndCompressBitmap()" + "Failed to delete file");
return false;
}
}
if (!file.createNewFile()) {
LogUtils.logE("ThumbnailUtils.copyAndCompressBitmap() "
+ "Failed to create file for bitmap stream");
return false;
}
/** Save Bitmap to file. **/
FileOutputStream stream = null;
try {
stream = new FileOutputStream(file);
if (stream == null) {
LogUtils.logE("ThumbnailUtils.copyAndCompressBitmap() "
+ "Failed to open stream for " + "file[" + file + "]");
return false;
}
if (!inputPhoto.compress(Bitmap.CompressFormat.PNG, PHOTO_QUALITY, stream)) {
LogUtils.logE("ThumbnailUtils.copyAndCompressBitmap() "
+ "Failed to store bitmap stream");
return false;
}
} finally {
CloseUtils.close(stream);
}
return true;
}
/***
* Saves an image in an ExternalResponseObject to the file system.
*
* @param localContactId Local contact ID if the new Thumbnail files.
* @param ext Given ExternalResponseObject to convert.
* @throws IOException File system issues.
*/
public static void saveExternalResponseObjectToFile(final long localContactId,
final ExternalResponseObject ext) throws IOException {
LogUtils.logI("DownloadServerThumbnails." + "saveExternalResponseObjectToFile() "
+ "Trying to save thumbnail.");
if (localContactId < 0) {
throw new InvalidParameterException("DownloadServerThumbnails."
+ "saveExternalResponseObjectToFile() LocalContactId must "
+ "be above 0, was[" + localContactId + "]");
}
if (ext == null) {
throw new InvalidParameterException("DownloadServerThumbnails."
+ "saveExternalResponseObjectToFile() "
+ "ExternalResponseObject must not be NULL");
}
LogUtils.logI("DownloadServerthumbnails." + "saveExternalResponseObjectToFile() mimeType["
+ ext.mMimeType + "]");
FileOutputStream fOut = null;
try {
fOut = new FileOutputStream(makeFile(localContactId));
fOut.write(ext.mBody);
LogUtils.logI("DownloadServerThumbnails."
+ "saveExternalResponseObjectToFile() Saved thumbnail.");
} catch (Exception e) {
LogUtils.logE("Exception in DownloadServerThumbnails."
+ "saveExternalResponseObjectToFile() " + e);
} finally {
CloseUtils.flush(fOut);
CloseUtils.close(fOut);
}
}
/***
* Creates a new File for the given Local Contact ID.
*
* @param localContactId Local contact ID if the new Thumbnail files.
* @return Newly created file.
* @throws IOException File system issue.
* @throws InvalidParameterException localContactId must be above 0.
*/
private static File makeFile(final long localContactId) throws IOException {
if (localContactId < 0) {
throw new InvalidParameterException("DownloadServerThumbnails."
+ "makeFile() LocalContactId must be above 0, was[" + localContactId + "]");
}
ensureThumbnailFolderExists();
File file = new File(ThumbnailUtils.THUMBNAIL_FILE_LOCATION + localContactId
+ PNG_EXTENSION);
if (!file.exists()) {
if (!file.createNewFile()) {
throw new IOException("DownloadServerThumbnails.makeFile() "
+ "Unable to create new file");
}
}
return file;
}
}