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.wallpaper.walkaround; 18 19 import android.service.wallpaper.WallpaperService; 20 import android.view.SurfaceHolder; 21 import android.hardware.Camera; 22 import android.util.Log; 23 import android.util.DisplayMetrics; 24 import android.graphics.Canvas; 25 import android.content.res.Configuration; 26 import android.content.res.Resources; 27 28 import java.io.IOException; 29 import java.util.List; 30 31 public class WalkAroundWallpaper extends WallpaperService { 32 private static final String LOG_TAG = "WalkAround"; 33 34 private Camera mCamera; 35 private WalkAroundEngine mOwner; 36 onCreateEngine()37 public Engine onCreateEngine() { 38 return mOwner = new WalkAroundEngine(); 39 } 40 41 @Override onDestroy()42 public void onDestroy() { 43 super.onDestroy(); 44 stopCamera(); 45 } 46 47 @Override onCreate()48 public void onCreate() { 49 super.onCreate(); 50 } 51 52 @Override onConfigurationChanged(Configuration newConfig)53 public void onConfigurationChanged(Configuration newConfig) { 54 super.onConfigurationChanged(newConfig); 55 56 if (mCamera != null) { 57 if (mCamera.previewEnabled()) { 58 boolean portrait = newConfig.orientation == Configuration.ORIENTATION_PORTRAIT; 59 final Camera.Parameters params = mCamera.getParameters(); 60 params.set("orientation", portrait ? "portrait" : "landscape"); 61 mCamera.setParameters(params); 62 63 if (mCamera.previewEnabled()) mCamera.stopPreview(); 64 mCamera.startPreview(); 65 } 66 } 67 } 68 startCamera()69 private void startCamera() { 70 if (mCamera == null) { 71 mCamera = Camera.open(); 72 } else { 73 try { 74 mCamera.reconnect(); 75 } catch (IOException e) { 76 mCamera.release(); 77 mCamera = null; 78 79 Log.e(LOG_TAG, "Error opening the camera", e); 80 } 81 } 82 } 83 stopCamera()84 private void stopCamera() { 85 if (mCamera != null) { 86 try { 87 mCamera.stopPreview(); 88 } catch (Exception e) { 89 // Ignore 90 } 91 92 try { 93 mCamera.release(); 94 } catch (Exception e) { 95 // Ignore 96 } 97 98 mCamera = null; 99 } 100 } 101 102 class WalkAroundEngine extends Engine { 103 private SurfaceHolder mHolder; 104 WalkAroundEngine()105 WalkAroundEngine() { 106 } 107 108 @Override onCreate(SurfaceHolder surfaceHolder)109 public void onCreate(SurfaceHolder surfaceHolder) { 110 super.onCreate(surfaceHolder); 111 112 surfaceHolder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS); 113 mHolder = surfaceHolder; 114 } 115 116 @Override onVisibilityChanged(boolean visible)117 public void onVisibilityChanged(boolean visible) { 118 if (!visible) { 119 if (mOwner == this) { 120 stopCamera(); 121 } 122 } else { 123 try { 124 startCamera(); 125 mCamera.setPreviewDisplay(mHolder); 126 startPreview(); 127 } catch (IOException e) { 128 mCamera.release(); 129 mCamera = null; 130 131 Log.e(LOG_TAG, "Error opening the camera", e); 132 } 133 } 134 } 135 136 @Override onSurfaceChanged(SurfaceHolder holder, int format, int width, int height)137 public void onSurfaceChanged(SurfaceHolder holder, int format, int width, int height) { 138 super.onSurfaceChanged(holder, format, width, height); 139 140 if (holder.isCreating()) { 141 try { 142 if (mCamera.previewEnabled()) mCamera.stopPreview(); 143 mCamera.setPreviewDisplay(holder); 144 } catch (IOException e) { 145 mCamera.release(); 146 mCamera = null; 147 148 Log.e(LOG_TAG, "Error opening the camera", e); 149 } 150 } 151 152 if (isVisible()) startPreview(); 153 } 154 155 @Override onSurfaceCreated(SurfaceHolder holder)156 public void onSurfaceCreated(SurfaceHolder holder) { 157 super.onSurfaceCreated(holder); 158 startCamera(); 159 } 160 startPreview()161 private void startPreview() { 162 final Resources resources = getResources(); 163 final boolean portrait = resources.getConfiguration().orientation == 164 Configuration.ORIENTATION_PORTRAIT; 165 166 final Camera.Parameters params = mCamera.getParameters(); 167 168 final DisplayMetrics metrics = resources.getDisplayMetrics(); 169 final List<Camera.Size> sizes = params.getSupportedPreviewSizes(); 170 171 // Try to find a preview size that matches the screen first 172 boolean found = false; 173 for (Camera.Size size : sizes) { 174 if ((portrait && 175 size.width == metrics.heightPixels && size.height == metrics.widthPixels) || 176 (!portrait && 177 size.width == metrics.widthPixels && size.height == metrics.heightPixels)) { 178 params.setPreviewSize(size.width, size.height); 179 found = true; 180 } 181 } 182 183 // If no suitable preview size was found, try to find something large enough 184 if (!found) { 185 for (Camera.Size size : sizes) { 186 if (size.width >= metrics.widthPixels && size.height >= metrics.heightPixels) { 187 params.setPreviewSize(size.width, size.height); 188 found = true; 189 } 190 } 191 } 192 193 // If no suitable preview size was found, pick the first one 194 if (!found) { 195 // Fill the canvas with black 196 Canvas canvas = null; 197 try { 198 canvas = mHolder.lockCanvas(); 199 if (canvas != null) canvas.drawColor(0); 200 } finally { 201 if (canvas != null) mHolder.unlockCanvasAndPost(canvas); 202 } 203 204 205 Camera.Size size = sizes.get(0); 206 params.setPreviewSize(size.width, size.height); 207 } 208 209 params.set("orientation", portrait ? "portrait" : "landscape"); 210 mCamera.setParameters(params); 211 212 mCamera.startPreview(); 213 } 214 } 215 } 216