Home | History | Annotate | Download | only in camera
      1 /*
      2  * Copyright (C) 2009 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 package com.android.camera;
     18 
     19 import com.android.gallery.R;
     20 
     21 import android.appwidget.AppWidgetManager;
     22 import android.appwidget.AppWidgetProvider;
     23 import android.content.ContentValues;
     24 import android.content.Context;
     25 import android.database.Cursor;
     26 import android.database.sqlite.SQLiteDatabase;
     27 import android.database.sqlite.SQLiteException;
     28 import android.database.sqlite.SQLiteOpenHelper;
     29 import android.graphics.Bitmap;
     30 import android.graphics.BitmapFactory;
     31 import android.util.Log;
     32 import android.widget.RemoteViews;
     33 
     34 import java.io.ByteArrayOutputStream;
     35 import java.io.IOException;
     36 
     37 /**
     38  * Simple widget to show a user-selected picture.
     39  */
     40 public class PhotoAppWidgetProvider extends AppWidgetProvider {
     41     private static final String TAG = "PhotoAppWidgetProvider";
     42     private static final boolean LOGD = true;
     43 
     44     @Override
     45     public void onUpdate(Context context, AppWidgetManager appWidgetManager,
     46                          int[] appWidgetIds) {
     47         // Update each requested appWidgetId with its unique photo
     48         PhotoDatabaseHelper helper = new PhotoDatabaseHelper(context);
     49         for (int appWidgetId : appWidgetIds) {
     50             int[] specificAppWidget = new int[] { appWidgetId };
     51             RemoteViews views = buildUpdate(context, appWidgetId, helper);
     52             if (LOGD) {
     53                 Log.d(TAG, "sending out views=" + views
     54                         + " for id=" + appWidgetId);
     55             }
     56             appWidgetManager.updateAppWidget(specificAppWidget, views);
     57         }
     58         helper.close();
     59     }
     60 
     61     @Override
     62     public void onDeleted(Context context, int[] appWidgetIds) {
     63         // Clean deleted photos out of our database
     64         PhotoDatabaseHelper helper = new PhotoDatabaseHelper(context);
     65         for (int appWidgetId : appWidgetIds) {
     66             helper.deletePhoto(appWidgetId);
     67         }
     68         helper.close();
     69     }
     70 
     71     /**
     72      * Load photo for given widget and build {@link RemoteViews} for it.
     73      */
     74     static RemoteViews buildUpdate(Context context, int appWidgetId,
     75                                    PhotoDatabaseHelper helper) {
     76         RemoteViews views = null;
     77         Bitmap bitmap = helper.getPhoto(appWidgetId);
     78         if (bitmap != null) {
     79             views = new RemoteViews(context.getPackageName(),
     80                                     R.layout.photo_frame);
     81             views.setImageViewBitmap(R.id.photo, bitmap);
     82         }
     83         return views;
     84     }
     85 
     86     static class PhotoDatabaseHelper extends SQLiteOpenHelper {
     87         private static final String DATABASE_NAME = "launcher.db";
     88 
     89         private static final int DATABASE_VERSION = 2;
     90 
     91         static final String TABLE_PHOTOS = "photos";
     92         static final String FIELD_APPWIDGET_ID = "appWidgetId";
     93         static final String FIELD_PHOTO_BLOB = "photoBlob";
     94 
     95         PhotoDatabaseHelper(Context context) {
     96             super(context, DATABASE_NAME, null, DATABASE_VERSION);
     97         }
     98 
     99         @Override
    100         public void onCreate(SQLiteDatabase db) {
    101             db.execSQL("CREATE TABLE " + TABLE_PHOTOS + " (" +
    102                     FIELD_APPWIDGET_ID + " INTEGER PRIMARY KEY," +
    103                     FIELD_PHOTO_BLOB + " BLOB" +
    104                     ");");
    105         }
    106 
    107         @Override
    108         public void onUpgrade(SQLiteDatabase db, int oldVersion,
    109                               int newVersion) {
    110             int version = oldVersion;
    111 
    112             if (version != DATABASE_VERSION) {
    113                 Log.w(TAG, "Destroying all old data.");
    114                 db.execSQL("DROP TABLE IF EXISTS " + TABLE_PHOTOS);
    115                 onCreate(db);
    116             }
    117         }
    118 
    119         /**
    120          * Store the given bitmap in this database for the given appWidgetId.
    121          */
    122         public boolean setPhoto(int appWidgetId, Bitmap bitmap) {
    123             boolean success = false;
    124             try {
    125                 // Try go guesstimate how much space the icon will take when
    126                 // serialized to avoid unnecessary allocations/copies during
    127                 // the write.
    128                 int size = bitmap.getWidth() * bitmap.getHeight() * 4;
    129                 ByteArrayOutputStream out = new ByteArrayOutputStream(size);
    130                 bitmap.compress(Bitmap.CompressFormat.PNG, 100, out);
    131                 out.flush();
    132                 out.close();
    133 
    134                 ContentValues values = new ContentValues();
    135                 values.put(PhotoDatabaseHelper.FIELD_APPWIDGET_ID, appWidgetId);
    136                 values.put(PhotoDatabaseHelper.FIELD_PHOTO_BLOB,
    137                            out.toByteArray());
    138 
    139                 SQLiteDatabase db = getWritableDatabase();
    140                 db.insertOrThrow(PhotoDatabaseHelper.TABLE_PHOTOS, null,
    141                                  values);
    142 
    143                 success = true;
    144             } catch (SQLiteException e) {
    145                 Log.e(TAG, "Could not open database", e);
    146             } catch (IOException e) {
    147                 Log.e(TAG, "Could not serialize photo", e);
    148             }
    149             if (LOGD) {
    150                 Log.d(TAG, "setPhoto success=" + success);
    151             }
    152             return success;
    153         }
    154 
    155         static final String[] PHOTOS_PROJECTION = {
    156             FIELD_PHOTO_BLOB,
    157         };
    158 
    159         static final int INDEX_PHOTO_BLOB = 0;
    160 
    161         /**
    162          * Inflate and return a bitmap for the given appWidgetId.
    163          */
    164         public Bitmap getPhoto(int appWidgetId) {
    165             Cursor c = null;
    166             Bitmap bitmap = null;
    167             try {
    168                 SQLiteDatabase db = getReadableDatabase();
    169                 String selection = String.format("%s=%d", FIELD_APPWIDGET_ID,
    170                                                  appWidgetId);
    171                 c = db.query(TABLE_PHOTOS, PHOTOS_PROJECTION, selection, null,
    172                         null, null, null, null);
    173 
    174                 if (c != null && LOGD) {
    175                     Log.d(TAG, "getPhoto query count=" + c.getCount());
    176                 }
    177 
    178                 if (c != null && c.moveToFirst()) {
    179                     byte[] data = c.getBlob(INDEX_PHOTO_BLOB);
    180                     if (data != null) {
    181                         bitmap = BitmapFactory.decodeByteArray(data, 0,
    182                                 data.length);
    183                     }
    184                 }
    185             } catch (SQLiteException e) {
    186                 Log.e(TAG, "Could not load photo from database", e);
    187             } finally {
    188                 if (c != null) {
    189                     c.close();
    190                 }
    191             }
    192             return bitmap;
    193         }
    194 
    195         /**
    196          * Remove any bitmap associated with the given appWidgetId.
    197          */
    198         public void deletePhoto(int appWidgetId) {
    199             try {
    200                 SQLiteDatabase db = getWritableDatabase();
    201                 String whereClause = String.format("%s=%d", FIELD_APPWIDGET_ID,
    202                                                    appWidgetId);
    203                 db.delete(TABLE_PHOTOS, whereClause, null);
    204             } catch (SQLiteException e) {
    205                 Log.e(TAG, "Could not delete photo from database", e);
    206             }
    207         }
    208     }
    209 
    210 }
    211 
    212