Home | History | Annotate | Download | only in media
      1 /*
      2  * Copyright (C) 2007 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.cooliris.media;
     18 
     19 import android.app.Activity;
     20 import android.app.ProgressDialog;
     21 import android.app.WallpaperManager;
     22 import android.content.Context;
     23 import android.content.Intent;
     24 import android.graphics.Bitmap;
     25 import android.graphics.BitmapFactory;
     26 import android.net.Uri;
     27 import android.os.Bundle;
     28 import android.os.Handler;
     29 import android.os.Message;
     30 import android.provider.MediaStore;
     31 import android.util.Log;
     32 
     33 import java.io.File;
     34 import java.io.FileInputStream;
     35 import java.io.FileNotFoundException;
     36 import java.io.IOException;
     37 import java.io.InputStream;
     38 
     39 import com.cooliris.app.Res;
     40 
     41 /**
     42  * Wallpaper picker for the camera application. This just redirects to the
     43  * standard pick action.
     44  */
     45 public class Wallpaper extends Activity {
     46     private static final String LOG_TAG = "Wallpaper";
     47     static final int PHOTO_PICKED = 1;
     48     static final int CROP_DONE = 2;
     49 
     50     static final int SHOW_PROGRESS = 0;
     51     static final int FINISH = 1;
     52 
     53     static final String DO_LAUNCH_ICICLE = "do_launch";
     54     static final String TEMP_FILE_PATH_ICICLE = "temp_file_path";
     55 
     56     private ProgressDialog mProgressDialog = null;
     57     private boolean mDoLaunch = true;
     58     private File mTempFile;
     59 
     60     private final Handler mHandler = new Handler() {
     61         @Override
     62         public void handleMessage(Message msg) {
     63             switch (msg.what) {
     64             case SHOW_PROGRESS: {
     65                 CharSequence c = getText(Res.string.wallpaper);
     66                 mProgressDialog = ProgressDialog.show(Wallpaper.this, "", c, true, false);
     67                 break;
     68             }
     69             case FINISH: {
     70                 closeProgressDialog();
     71                 setResult(RESULT_OK);
     72                 finish();
     73                 break;
     74             }
     75             }
     76         }
     77     };
     78 
     79     static class SetWallpaperThread extends Thread {
     80         private final Bitmap mBitmap;
     81         private final Handler mHandler;
     82         private final Context mContext;
     83         private final File mFile;
     84 
     85         public SetWallpaperThread(Bitmap bitmap, Handler handler, Context context, File file) {
     86             mBitmap = bitmap;
     87             mHandler = handler;
     88             mContext = context;
     89             mFile = file;
     90         }
     91 
     92         @Override
     93         public void run() {
     94             try {
     95                 WallpaperManager.getInstance(mContext).setBitmap(mBitmap);
     96             } catch (IOException e) {
     97                 Log.e(LOG_TAG, "Failed to set wallpaper.", e);
     98             } finally {
     99                 mHandler.sendEmptyMessage(FINISH);
    100                 mFile.delete();
    101             }
    102         }
    103     }
    104 
    105     private synchronized void closeProgressDialog() {
    106         if (mProgressDialog != null) {
    107             mProgressDialog.dismiss();
    108             mProgressDialog = null;
    109         }
    110     }
    111 
    112     @Override
    113     protected void onCreate(Bundle icicle) {
    114         super.onCreate(icicle);
    115         if (icicle != null) {
    116             mDoLaunch = icicle.getBoolean(DO_LAUNCH_ICICLE);
    117             mTempFile = new File(icicle.getString(TEMP_FILE_PATH_ICICLE));
    118         }
    119     }
    120 
    121     @Override
    122     protected void onSaveInstanceState(Bundle icicle) {
    123         icicle.putBoolean(DO_LAUNCH_ICICLE, mDoLaunch);
    124         icicle.putString(TEMP_FILE_PATH_ICICLE, mTempFile.getAbsolutePath());
    125     }
    126 
    127     @Override
    128     protected void onPause() {
    129         closeProgressDialog();
    130         super.onPause();
    131     }
    132 
    133     @Override
    134     protected void onResume() {
    135         super.onResume();
    136         if (!mDoLaunch) {
    137             return;
    138         }
    139         Uri imageToUse = getIntent().getData();
    140         if (imageToUse != null) {
    141             Intent intent = new Intent();
    142             intent.setClass(this, CropImage.class);
    143             intent.setData(imageToUse);
    144             formatIntent(intent);
    145             startActivityForResult(intent, CROP_DONE);
    146         } else {
    147             Intent intent = new Intent(Intent.ACTION_GET_CONTENT, null);
    148             intent.setType("image/*");
    149             intent.putExtra("crop", "true");
    150             formatIntent(intent);
    151             startActivityForResult(intent, PHOTO_PICKED);
    152         }
    153     }
    154 
    155     protected void formatIntent(Intent intent) {
    156         // TODO: A temporary file is NOT necessary
    157         // The CropImage intent should be able to set the wallpaper directly
    158         // without writing to a file, which we then need to read here to write
    159         // it again as the final wallpaper, this is silly
    160         mTempFile = getFileStreamPath("temp-wallpaper");
    161         mTempFile.getParentFile().mkdirs();
    162 
    163         int width = getWallpaperDesiredMinimumWidth();
    164         int height = getWallpaperDesiredMinimumHeight();
    165         intent.putExtra("outputX", width);
    166         intent.putExtra("outputY", height);
    167         intent.putExtra("aspectX", width);
    168         intent.putExtra("aspectY", height);
    169         intent.putExtra("scale", true);
    170         intent.putExtra("noFaceDetection", true);
    171         intent.putExtra(MediaStore.EXTRA_OUTPUT, Uri.fromFile(mTempFile));
    172         intent.putExtra("outputFormat", Bitmap.CompressFormat.PNG.name());
    173         // TODO: we should have an extra called "setWallpaper" to ask CropImage
    174         // to set the cropped image as a wallpaper directly. This means the
    175         // SetWallpaperThread should be moved out of this class to CropImage
    176     }
    177 
    178     @Override
    179     protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    180         if ((requestCode == PHOTO_PICKED || requestCode == CROP_DONE) && (resultCode == RESULT_OK) && (data != null)) {
    181             try {
    182                 InputStream s = new FileInputStream(mTempFile);
    183                 try {
    184                     Bitmap bitmap = BitmapFactory.decodeStream(s);
    185                     if (bitmap == null) {
    186                         Log.e(LOG_TAG, "Failed to set wallpaper. " + "Couldn't get bitmap for path " + mTempFile);
    187                     } else {
    188                         mHandler.sendEmptyMessage(SHOW_PROGRESS);
    189                         new SetWallpaperThread(bitmap, mHandler, this, mTempFile).start();
    190                     }
    191                     mDoLaunch = false;
    192                 } finally {
    193                     Util.closeSilently(s);
    194                 }
    195             } catch (FileNotFoundException ex) {
    196                 Log.e(LOG_TAG, "file not found: " + mTempFile, ex);
    197             }
    198         } else {
    199             setResult(RESULT_CANCELED);
    200             finish();
    201         }
    202     }
    203 }
    204