VideoCamera.java revision 9bc8d1b47e5bab978cc9571ddfdedc8309a0b65d
1b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project/* 2b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project * Copyright (C) 2007 The Android Open Source Project 3b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project * 4b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project * Licensed under the Apache License, Version 2.0 (the "License"); 5b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project * you may not use this file except in compliance with the License. 6b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project * You may obtain a copy of the License at 7b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project * 8b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project * http://www.apache.org/licenses/LICENSE-2.0 9b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project * 10b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project * Unless required by applicable law or agreed to in writing, software 11b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project * distributed under the License is distributed on an "AS IS" BASIS, 12b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project * See the License for the specific language governing permissions and 14b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project * limitations under the License. 15b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project */ 16b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 17b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectpackage com.android.camera; 18b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 19b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport java.io.File; 20b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport java.io.FileDescriptor; 21b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport java.io.IOException; 22b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport java.text.SimpleDateFormat; 23b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport java.util.ArrayList; 24b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport java.util.Date; 25b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 26b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.app.Activity; 27b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.content.BroadcastReceiver; 28b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.content.ContentResolver; 29b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.content.ContentValues; 30b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.content.Context; 31b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.content.Intent; 32b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.content.IntentFilter; 33b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.content.SharedPreferences; 349bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Changimport android.database.Cursor; 35b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.graphics.Bitmap; 36b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.graphics.drawable.Drawable; 37b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.location.LocationManager; 38b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.media.MediaRecorder; 39b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.net.Uri; 40b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.os.Bundle; 41b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.os.Environment; 42b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.os.Handler; 43b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.os.Message; 44b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.os.StatFs; 45b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.os.SystemClock; 46b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.preference.PreferenceManager; 47b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.provider.MediaStore; 48b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.provider.MediaStore.Video; 49b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.text.format.DateFormat; 50b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.util.Log; 51b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.view.KeyEvent; 52b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.view.Menu; 53b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.view.MenuItem; 54b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.view.SurfaceHolder; 55b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.view.View; 56b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.view.Window; 57b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.view.WindowManager; 58b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.view.MenuItem.OnMenuItemClickListener; 59b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.view.animation.AlphaAnimation; 60b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.view.animation.Animation; 61b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.widget.ImageView; 62b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.widget.TextView; 63b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectimport android.widget.Toast; 64b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 65b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Projectpublic class VideoCamera extends Activity implements View.OnClickListener, 668d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project ShutterButton.OnShutterButtonListener, SurfaceHolder.Callback, MediaRecorder.OnErrorListener, MediaRecorder.OnInfoListener { 67b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 68b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private static final String TAG = "videocamera"; 69b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 70b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private static final boolean DEBUG = true; 71b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private static final boolean DEBUG_SUPPRESS_AUDIO_RECORDING = DEBUG && false; 72b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 73b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private static final int CLEAR_SCREEN_DELAY = 4; 74b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private static final int UPDATE_RECORD_TIME = 5; 75b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 76b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private static final int SCREEN_DELAY = 2 * 60 * 1000; 77b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 78b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private static final long NO_STORAGE_ERROR = -1L; 79b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private static final long CANNOT_STAT_ERROR = -2L; 80b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private static final long LOW_STORAGE_THRESHOLD = 512L * 1024L; 81e3f4516c2154539cb5778ef061abf8a0ccf90a5eThe Android Open Source Project private static final long SHARE_FILE_LENGTH_LIMIT = 3L * 1024L * 1024L; 82b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 839a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project private static final int STORAGE_STATUS_OK = 0; 849a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project private static final int STORAGE_STATUS_LOW = 1; 859a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project private static final int STORAGE_STATUS_NONE = 2; 869a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project 87b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public static final int MENU_SETTINGS = 6; 88b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public static final int MENU_GALLERY_PHOTOS = 7; 89b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public static final int MENU_GALLERY_VIDEOS = 8; 90b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public static final int MENU_SAVE_GALLERY_PHOTO = 34; 91b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public static final int MENU_SAVE_PLAY_VIDEO = 35; 92b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public static final int MENU_SAVE_SELECT_VIDEO = 36; 93b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public static final int MENU_SAVE_NEW_VIDEO = 37; 94b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 95b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project SharedPreferences mPreferences; 96b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 97b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private static final float VIDEO_ASPECT_RATIO = 176.0f / 144.0f; 98b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project VideoPreview mVideoPreview; 99b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project SurfaceHolder mSurfaceHolder = null; 100b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project ImageView mVideoFrame; 1019bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang 1029bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang private boolean mIsVideoCaptureIntent; 1039bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang // mLastPictureButton and mThumbController 1049bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang // are non-null only if isVideoCaptureIntent() is true; 105de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project private ImageView mLastPictureButton; 1069bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang private ThumbnailController mThumbController; 107b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 1088d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project private static final int MAX_RECORDING_DURATION_MS = 10 * 60 * 1000; 1098d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project 1109a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project private int mStorageStatus = STORAGE_STATUS_OK; 1119a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project 112b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private MediaRecorder mMediaRecorder; 113b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private boolean mMediaRecorderRecording = false; 114b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private long mRecordingStartTime; 115b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // The video file that the hardware camera is about to record into 116b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // (or is recording into.) 117b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private String mCameraVideoFilename; 118b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private FileDescriptor mCameraVideoFileDescriptor; 119b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 120b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // The video file that has already been recorded, and that is being 121b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // examined by the user. 122b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private String mCurrentVideoFilename; 1238d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project private long mCurrentVideoFileLength = 0L; 124b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private Uri mCurrentVideoUri; 125b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private ContentValues mCurrentVideoValues; 126b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 127b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project boolean mPausing = false; 128b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 129b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project static ContentResolver mContentResolver; 130b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 131b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project int mCurrentZoomIndex = 0; 132b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 133b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private ShutterButton mShutterButton; 134b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private TextView mRecordingTimeView; 1358d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project private boolean mRecordingTimeCountsDown = false; 136b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 137b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project ArrayList<MenuItem> mGalleryItems = new ArrayList<MenuItem>(); 138b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 139b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project View mPostPictureAlert; 140b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project LocationManager mLocationManager = null; 141b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 142b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private Handler mHandler = new MainHandler(); 143b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 144b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project /** This Handler is used to post message back onto the main thread of the application */ 145b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private class MainHandler extends Handler { 146b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project @Override 147b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public void handleMessage(Message msg) { 148b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project switch (msg.what) { 149b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 150b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project case CLEAR_SCREEN_DELAY: { 151b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project clearScreenOnFlag(); 152b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project break; 153b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 154b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 155b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project case UPDATE_RECORD_TIME: { 156b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (mMediaRecorderRecording) { 157b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project long now = SystemClock.uptimeMillis(); 158b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project long delta = now - mRecordingStartTime; 1598d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project 1608d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project // Starting a minute before reaching the max duration 1618d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project // limit, we'll countdown the remaining time instead. 1628d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project boolean countdown_remaining_time = 1638d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project (delta >= MAX_RECORDING_DURATION_MS - 60000); 1648d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project 1658d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project if (countdown_remaining_time) { 1668d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project delta = Math.max(0, MAX_RECORDING_DURATION_MS - delta); 1678d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project } 1688d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project 1698d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project long seconds = (delta + 500) / 1000; // round to nearest 170b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project long minutes = seconds / 60; 171b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project long hours = minutes / 60; 172b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project long remainderMinutes = minutes - (hours * 60); 173b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project long remainderSeconds = seconds - (minutes * 60); 174b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 175b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project String secondsString = Long.toString(remainderSeconds); 176b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (secondsString.length() < 2) { 177b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project secondsString = "0" + secondsString; 178b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 179b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project String minutesString = Long.toString(remainderMinutes); 180b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (minutesString.length() < 2) { 181b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project minutesString = "0" + minutesString; 182b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 183b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project String text = minutesString + ":" + secondsString; 184b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (hours > 0) { 185b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project String hoursString = Long.toString(hours); 186b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (hoursString.length() < 2) { 187b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project hoursString = "0" + hoursString; 188b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 189b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project text = hoursString + ":" + text; 190b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 191b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mRecordingTimeView.setText(text); 1928d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project 1938d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project if (mRecordingTimeCountsDown != countdown_remaining_time) { 1948d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project // Avoid setting the color on every update, do it only 1958d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project // when it needs changing. 1968d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project 1978d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project mRecordingTimeCountsDown = countdown_remaining_time; 1988d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project 1998d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project int color = getResources().getColor( 2008d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project countdown_remaining_time ? R.color.recording_time_remaining_text 2018d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project : R.color.recording_time_elapsed_text); 2028d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project 2038d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project mRecordingTimeView.setTextColor(color); 2048d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project } 2058d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project 206b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // Work around a limitation of the T-Mobile G1: The T-Mobile 207b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // hardware blitter can't pixel-accurately scale and clip at the same time, 208b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // and the SurfaceFlinger doesn't attempt to work around this limitation. 209b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // In order to avoid visual corruption we must manually refresh the entire 210b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // surface view when changing any overlapping view's contents. 211b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mVideoPreview.invalidate(); 212b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mHandler.sendEmptyMessageDelayed(UPDATE_RECORD_TIME, 1000); 213b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 214b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project break; 215b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 216b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 217b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project default: 218b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Log.v(TAG, "Unhandled message: " + msg.what); 219b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project break; 220b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 221b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 222b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project }; 223b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 224b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private final BroadcastReceiver mReceiver = new BroadcastReceiver() { 225b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project @Override 226b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public void onReceive(Context context, Intent intent) { 227b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project String action = intent.getAction(); 228b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (action.equals(Intent.ACTION_MEDIA_EJECT)) { 2299a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project updateAndShowStorageHint(false); 230b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project stopVideoRecording(); 231b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project initializeVideo(); 232b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } else if (action.equals(Intent.ACTION_MEDIA_MOUNTED)) { 2339a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project updateAndShowStorageHint(true); 234b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project initializeVideo(); 235b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } else if (action.equals(Intent.ACTION_MEDIA_UNMOUNTED)) { 236b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // SD card unavailable 2379a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project // handled in ACTION_MEDIA_EJECT 238b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } else if (action.equals(Intent.ACTION_MEDIA_SCANNER_STARTED)) { 239b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Toast.makeText(VideoCamera.this, getResources().getString(R.string.wait), 5000); 240b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } else if (action.equals(Intent.ACTION_MEDIA_SCANNER_FINISHED)) { 2419a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project updateAndShowStorageHint(true); 242b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 243b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 244b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project }; 245b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 246b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project static private String createName(long dateTaken) { 247b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return DateFormat.format("yyyy-MM-dd kk.mm.ss", dateTaken).toString(); 248b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 249b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 250b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project /** Called with the activity is first created. */ 251b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project @Override 252b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public void onCreate(Bundle icicle) { 253b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project super.onCreate(icicle); 254b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 255b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mLocationManager = (LocationManager) getSystemService(Context.LOCATION_SERVICE); 256b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 257b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mPreferences = PreferenceManager.getDefaultSharedPreferences(this); 258b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mContentResolver = getContentResolver(); 259b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 260b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project //setDefaultKeyMode(DEFAULT_KEYS_SHORTCUT); 261b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project requestWindowFeature(Window.FEATURE_PROGRESS); 262b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project setContentView(R.layout.video_camera); 263b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 264b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mVideoPreview = (VideoPreview) findViewById(R.id.camera_preview); 265b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mVideoPreview.setAspectRatio(VIDEO_ASPECT_RATIO); 266b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 267b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // don't set mSurfaceHolder here. We have it set ONLY within 268b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // surfaceCreated / surfaceDestroyed, other parts of the code 269b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // assume that when it is set, the surface is also set. 270b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project SurfaceHolder holder = mVideoPreview.getHolder(); 271b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project holder.addCallback(this); 272b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project holder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS); 273b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 274b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mPostPictureAlert = findViewById(R.id.post_picture_panel); 275b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 276b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project int[] ids = new int[]{R.id.play, R.id.share, R.id.discard, 277b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project R.id.cancel, R.id.attach}; 278b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project for (int id : ids) { 279b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project findViewById(id).setOnClickListener(this); 280b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 281b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 282b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mShutterButton = (ShutterButton) findViewById(R.id.shutter_button); 283b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mShutterButton.setOnShutterButtonListener(this); 284b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mRecordingTimeView = (TextView) findViewById(R.id.recording_time); 285b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mVideoFrame = (ImageView) findViewById(R.id.video_frame); 2869bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang mIsVideoCaptureIntent = isVideoCaptureIntent(); 2879bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang if (!mIsVideoCaptureIntent) { 2889bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang mLastPictureButton = (ImageView) findViewById(R.id.last_picture_button); 2899bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang mLastPictureButton.setOnClickListener(this); 2909bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang Drawable frame = getResources().getDrawable(R.drawable.frame_thumbnail); 2919bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang mThumbController = new ThumbnailController(mLastPictureButton, 2929bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang frame, mContentResolver); 2939bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang mThumbController.loadData(ImageManager.getLastVideoThumbPath()); 2949bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang } 295b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 296b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 297e3f4516c2154539cb5778ef061abf8a0ccf90a5eThe Android Open Source Project private void startShareVideoActivity() { 2988d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project if (mCurrentVideoFileLength > SHARE_FILE_LENGTH_LIMIT) { 299e3f4516c2154539cb5778ef061abf8a0ccf90a5eThe Android Open Source Project Toast.makeText(VideoCamera.this, 300e3f4516c2154539cb5778ef061abf8a0ccf90a5eThe Android Open Source Project R.string.too_large_to_attach, Toast.LENGTH_LONG).show(); 301e3f4516c2154539cb5778ef061abf8a0ccf90a5eThe Android Open Source Project return; 302e3f4516c2154539cb5778ef061abf8a0ccf90a5eThe Android Open Source Project } 303e3f4516c2154539cb5778ef061abf8a0ccf90a5eThe Android Open Source Project Intent intent = new Intent(); 304e3f4516c2154539cb5778ef061abf8a0ccf90a5eThe Android Open Source Project intent.setAction(Intent.ACTION_SEND); 305e3f4516c2154539cb5778ef061abf8a0ccf90a5eThe Android Open Source Project intent.setType("video/3gpp"); 306e3f4516c2154539cb5778ef061abf8a0ccf90a5eThe Android Open Source Project intent.putExtra(Intent.EXTRA_STREAM, mCurrentVideoUri); 307e3f4516c2154539cb5778ef061abf8a0ccf90a5eThe Android Open Source Project try { 308e3f4516c2154539cb5778ef061abf8a0ccf90a5eThe Android Open Source Project startActivity(Intent.createChooser(intent, getText(R.string.sendVideo))); 309e3f4516c2154539cb5778ef061abf8a0ccf90a5eThe Android Open Source Project } catch (android.content.ActivityNotFoundException ex) { 310e3f4516c2154539cb5778ef061abf8a0ccf90a5eThe Android Open Source Project Toast.makeText(VideoCamera.this, R.string.no_way_to_share_video, Toast.LENGTH_SHORT).show(); 311e3f4516c2154539cb5778ef061abf8a0ccf90a5eThe Android Open Source Project } 312e3f4516c2154539cb5778ef061abf8a0ccf90a5eThe Android Open Source Project } 313e3f4516c2154539cb5778ef061abf8a0ccf90a5eThe Android Open Source Project 314b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public void onClick(View v) { 315b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project switch (v.getId()) { 316b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 317b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project case R.id.gallery: 318b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project MenuHelper.gotoCameraVideoGallery(this); 319b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project break; 320b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 321b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project case R.id.attach: 322b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project doReturnToCaller(true); 323b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project break; 324b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 325b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project case R.id.cancel: 326b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project doReturnToCaller(false); 327b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project break; 328b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 329b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project case R.id.discard: { 330b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project discardCurrentVideoAndStartPreview(); 331b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project break; 332b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 333b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 334b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project case R.id.share: { 335e3f4516c2154539cb5778ef061abf8a0ccf90a5eThe Android Open Source Project startShareVideoActivity(); 336b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project break; 337b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 338b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 339b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project case R.id.play: { 340b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project doPlayCurrentVideo(); 341b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project break; 342b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 343de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project 344de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project case R.id.last_picture_button: { 3459bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang stopVideoRecordingAndShowAlert(); 346de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project break; 347de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project } 348b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 349b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 350b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 351b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public void onShutterButtonFocus(ShutterButton button, boolean pressed) { 352de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project // Do nothing (everything happens in onShutterButtonClick). 353de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project } 354de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project 355de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project public void onShutterButtonClick(ShutterButton button) { 356b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project switch (button.getId()) { 357b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project case R.id.shutter_button: 358de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project if (mMediaRecorderRecording) { 3599bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang if (mIsVideoCaptureIntent) { 360de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project stopVideoRecordingAndShowAlert(); 361b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } else { 3629bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang stopVideoRecordingAndGetThumbnail(); 3639bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang initializeVideo(); 3649bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang } 3659bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang } else if (isAlertVisible()) { 3669bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang if (mIsVideoCaptureIntent) { 3679bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang discardCurrentVideoAndStartPreview(); 3689bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang } else { 3699bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang hideAlertAndStartVideoRecording(); 370b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 371de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project } else { 372de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project startVideoRecording(); 373b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 374b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project break; 375b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 376b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 377b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 378b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private void doPlayCurrentVideo() { 379b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Log.e(TAG, "Playing current video: " + mCurrentVideoUri); 380b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Intent intent = new Intent(Intent.ACTION_VIEW, mCurrentVideoUri); 381b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project try { 382b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project startActivity(intent); 383b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } catch (android.content.ActivityNotFoundException ex) { 384b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Log.e(TAG, "Couldn't view video " + mCurrentVideoUri, ex); 385b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 386b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 387b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 388b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private void discardCurrentVideoAndStartPreview() { 389b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project deleteCurrentVideo(); 3909bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang hideAlertAndStartPreview(); 391b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 392b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 393b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private OnScreenHint mStorageHint; 394b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 3959a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project private void updateAndShowStorageHint(boolean mayHaveSd) { 3969a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project mStorageStatus = getStorageStatus(mayHaveSd); 3979a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project showStorageHint(); 3989a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project } 3999a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project 4009a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project private void showStorageHint() { 401b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project String errorMessage = null; 4029a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project switch (mStorageStatus) { 4039a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project case STORAGE_STATUS_NONE: 404b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project errorMessage = getString(R.string.no_storage); 4059a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project break; 4069a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project case STORAGE_STATUS_LOW: 407b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project errorMessage = getString(R.string.spaceIsLow_content); 408b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 409b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (errorMessage != null) { 410b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (mStorageHint == null) { 411b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mStorageHint = OnScreenHint.makeText(this, errorMessage); 412b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } else { 413b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mStorageHint.setText(errorMessage); 414b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 415b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mStorageHint.show(); 416b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } else if (mStorageHint != null) { 417b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mStorageHint.cancel(); 418b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mStorageHint = null; 419b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 420b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 421b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 4229a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project private int getStorageStatus(boolean mayHaveSd) { 4239a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project long remaining = mayHaveSd ? getAvailableStorage() : NO_STORAGE_ERROR; 4249a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project if (remaining == NO_STORAGE_ERROR) { 4259a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project return STORAGE_STATUS_NONE; 4269a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project } 4279a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project return remaining < LOW_STORAGE_THRESHOLD 4289a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project ? STORAGE_STATUS_LOW : STORAGE_STATUS_OK; 4299a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project } 4309a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project 431b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project @Override 432b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public void onResume() { 433b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project super.onResume(); 434b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 435b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project setScreenTimeoutLong(); 436b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 437b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mPausing = false; 438b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 439b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // install an intent filter to receive SD card related events. 440b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project IntentFilter intentFilter = new IntentFilter(Intent.ACTION_MEDIA_MOUNTED); 441b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project intentFilter.addAction(Intent.ACTION_MEDIA_EJECT); 442b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project intentFilter.addAction(Intent.ACTION_MEDIA_UNMOUNTED); 443b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project intentFilter.addAction(Intent.ACTION_MEDIA_SCANNER_STARTED); 444b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project intentFilter.addAction(Intent.ACTION_MEDIA_SCANNER_FINISHED); 445b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project intentFilter.addDataScheme("file"); 446b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project registerReceiver(mReceiver, intentFilter); 4479a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project mStorageStatus = getStorageStatus(true); 4489a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project 4499a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project mHandler.postDelayed(new Runnable() { 4509a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project public void run() { 4519a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project showStorageHint(); 4529a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project } 4539a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project }, 200); 454b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 4559bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang initializeVideo(); 456b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 457b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 458b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project @Override 459b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public void onStop() { 460b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project setScreenTimeoutSystemDefault(); 461b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project super.onStop(); 462b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 463b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 464b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project @Override 465b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project protected void onPause() { 466b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project super.onPause(); 467b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 4689bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang // This is similar to what mShutterButton.performClick() does, 4699bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang // but not quite the same. 4709bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang if (mMediaRecorderRecording) { 4719bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang if (mIsVideoCaptureIntent) { 4729bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang stopVideoRecordingAndShowAlert(); 4739bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang } else { 4749bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang stopVideoRecordingAndGetThumbnail(); 4759bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang } 4769bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang } else { 4779bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang stopVideoRecording(); 4789bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang } 479b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 480b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mPausing = true; 481b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 4829c9be2eb4a86fc3468dbba1ec5f7bfdb37d22c74The Android Open Source Project unregisterReceiver(mReceiver); 483b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project setScreenTimeoutSystemDefault(); 484b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 4859bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang if (!mIsVideoCaptureIntent) { 4869bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang mThumbController.storeData(ImageManager.getLastVideoThumbPath()); 4879bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang } 4889bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang 489b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (mStorageHint != null) { 490b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mStorageHint.cancel(); 491b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mStorageHint = null; 492b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 493b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 494b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 495b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project @Override 496b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public boolean onKeyDown(int keyCode, KeyEvent event) { 497b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project setScreenTimeoutLong(); 498b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 499b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project switch (keyCode) { 500b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project case KeyEvent.KEYCODE_BACK: 501b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (mMediaRecorderRecording) { 502de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project mShutterButton.performClick(); 503b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return true; 5049bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang } else if(isAlertVisible()) { 5059bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang hideAlertAndStartPreview(); 506b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return true; 507b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 508b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project break; 509b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project case KeyEvent.KEYCODE_CAMERA: 510b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (event.getRepeatCount() == 0) { 511de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project mShutterButton.performClick(); 512b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return true; 513b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 514de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project break; 515b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project case KeyEvent.KEYCODE_DPAD_CENTER: 516b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (event.getRepeatCount() == 0) { 517de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project mShutterButton.performClick(); 518de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project return true; 519b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 520b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project break; 521b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project case KeyEvent.KEYCODE_MENU: 522b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (mMediaRecorderRecording) { 523de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project mShutterButton.performClick(); 524b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return true; 525b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 526b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project break; 527b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 528b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 529b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return super.onKeyDown(keyCode, event); 530b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 531b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 532b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project @Override 533b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public boolean onKeyUp(int keyCode, KeyEvent event) { 534b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project switch(keyCode) { 535b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project case KeyEvent.KEYCODE_CAMERA: 536b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mShutterButton.setPressed(false); 537b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return true; 538b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 539b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return super.onKeyUp(keyCode, event); 540b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 541b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 542b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public void surfaceChanged(SurfaceHolder holder, int format, int w, int h) { 543b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project stopVideoRecording(); 544b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project initializeVideo(); 545b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 546b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 547b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public void surfaceCreated(SurfaceHolder holder) { 548b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mSurfaceHolder = holder; 549b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 550b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 551b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public void surfaceDestroyed(SurfaceHolder holder) { 552b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mSurfaceHolder = null; 553b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 554b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 555b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project void gotoGallery() { 556b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project MenuHelper.gotoCameraVideoGallery(this); 557b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 558b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 559b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project @Override 560b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public boolean onPrepareOptionsMenu(Menu menu) { 561b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project super.onPrepareOptionsMenu(menu); 562b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 563b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project for (int i = 1; i <= MenuHelper.MENU_ITEM_MAX; i++) { 564b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (i != MenuHelper.GENERIC_ITEM) { 565b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project menu.setGroupVisible(i, false); 566b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 567b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 568b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 569b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project menu.setGroupVisible(MenuHelper.VIDEO_MODE_ITEM, true); 570b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return true; 571b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 572b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 573b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project @Override 574b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public boolean onCreateOptionsMenu(Menu menu) { 575b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project super.onCreateOptionsMenu(menu); 576b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 5779bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang if (mIsVideoCaptureIntent) { 578b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // No options menu for attach mode. 579b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return false; 580b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } else { 581b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project addBaseMenuItems(menu); 582b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project MenuHelper.addImageMenuItems( 583b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project menu, 584b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project MenuHelper.INCLUDE_ALL & ~MenuHelper.INCLUDE_ROTATE_MENU, 585b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project false, 586b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project VideoCamera.this, 587b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mHandler, 588b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 589b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // Handler for deletion 590b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project new Runnable() { 591b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public void run() { 592b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // What do we do here? 593b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // mContentResolver.delete(uri, null, null); 594b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 595b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project }, 596b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project new MenuHelper.MenuInvoker() { 597b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public void run(final MenuHelper.MenuCallback cb) { 598b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 599b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project }); 600b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 601b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project MenuItem gallery = menu.add(MenuHelper.IMAGE_SAVING_ITEM, MENU_SAVE_GALLERY_PHOTO, 0, 602b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project R.string.camera_gallery_photos_text).setOnMenuItemClickListener( 603b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project new MenuItem.OnMenuItemClickListener() { 604b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public boolean onMenuItemClick(MenuItem item) { 605b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project gotoGallery(); 606b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return true; 607b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 608b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project }); 609b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project gallery.setIcon(android.R.drawable.ic_menu_gallery); 610b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 611b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return true; 612b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 613b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 614b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private boolean isVideoCaptureIntent() { 615b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project String action = getIntent().getAction(); 616b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return (MediaStore.ACTION_VIDEO_CAPTURE.equals(action)); 617b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 618b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 619b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private void doReturnToCaller(boolean success) { 620b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Intent resultIntent = new Intent(); 621b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project int resultCode; 622b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (success) { 623b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project resultCode = RESULT_OK; 624b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project resultIntent.setData(mCurrentVideoUri); 625b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } else { 626b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project resultCode = RESULT_CANCELED; 627b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 628b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project setResult(resultCode, resultIntent); 629b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project finish(); 630b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 631b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 632b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project /** 633b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project * Returns 634b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project * @return number of bytes available, or an ERROR code. 635b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project */ 636b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private static long getAvailableStorage() { 637b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project try { 638b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (!ImageManager.hasStorage()) { 639b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return NO_STORAGE_ERROR; 640b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } else { 641b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project String storageDirectory = Environment.getExternalStorageDirectory().toString(); 642b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project StatFs stat = new StatFs(storageDirectory); 643b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return ((long)stat.getAvailableBlocks() * (long)stat.getBlockSize()); 644b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 645b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } catch (Exception ex) { 646b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // if we can't stat the filesystem then we don't know how many 647b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // free bytes exist. It might be zero but just leave it 648b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // blank since we really don't know. 649b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return CANNOT_STAT_ERROR; 650b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 651b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 652b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 653b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private void cleanupEmptyFile() { 654b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (mCameraVideoFilename != null) { 655b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project File f = new File(mCameraVideoFilename); 656b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (f.length() == 0 && f.delete()) { 657b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Log.v(TAG, "Empty video file deleted: " + mCameraVideoFilename); 658b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mCameraVideoFilename = null; 659b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 660b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 661b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 662b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 6639bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang // initializeVideo() starts preview and prepare media recorder. 664b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // Returns false if initializeVideo fails 665b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private boolean initializeVideo() { 666b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Log.v(TAG, "initializeVideo"); 6679bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang 6689bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang // We will call initializeVideo() again when the alert is hidden. 6699bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang if (isAlertVisible()) return false; 6709bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang 671b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Intent intent = getIntent(); 672b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Bundle myExtras = intent.getExtras(); 673b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 6749bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang if (mIsVideoCaptureIntent && myExtras != null) { 675b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Uri saveUri = (Uri) myExtras.getParcelable(MediaStore.EXTRA_OUTPUT); 676b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (saveUri != null) { 677b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project try { 678b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mCameraVideoFileDescriptor = mContentResolver. 679b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project openFileDescriptor(saveUri, "rw").getFileDescriptor(); 680b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mCurrentVideoUri = saveUri; 681b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 682b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project catch (java.io.FileNotFoundException ex) { 683b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // invalid uri 684b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Log.e(TAG, ex.toString()); 685b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 686b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 687b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 688b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project releaseMediaRecorder(); 689b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 690b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (mSurfaceHolder == null) { 691b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Log.v(TAG, "SurfaceHolder is null"); 692b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return false; 693b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 694b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 695b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mMediaRecorder = new MediaRecorder(); 696b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 697b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (DEBUG_SUPPRESS_AUDIO_RECORDING) { 698b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Log.v(TAG, "DEBUG_SUPPRESS_AUDIO_RECORDING is true."); 699b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } else { 700b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mMediaRecorder.setAudioSource(MediaRecorder.AudioSource.MIC); 701b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 702b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mMediaRecorder.setVideoSource(MediaRecorder.VideoSource.CAMERA); 703b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mMediaRecorder.setOutputFormat(MediaRecorder.OutputFormat.THREE_GPP); 704b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 7058d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project mMediaRecorder.setMaxDuration(MAX_RECORDING_DURATION_MS); 7068d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project 7079a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project if (mStorageStatus != STORAGE_STATUS_OK) { 708b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mMediaRecorder.setOutputFile("/dev/null"); 709b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } else { 710b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // We try Uri in intent first. If it doesn't work, use our own instead. 711b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (mCameraVideoFileDescriptor != null) { 712b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mMediaRecorder.setOutputFile(mCameraVideoFileDescriptor); 713b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } else { 714b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project createVideoPath(); 715b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mMediaRecorder.setOutputFile(mCameraVideoFilename); 716b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 717b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 718b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 719b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project boolean videoQualityHigh = getBooleanPreference(CameraSettings.KEY_VIDEO_QUALITY, 720b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project CameraSettings.DEFAULT_VIDEO_QUALITY_VALUE); 721b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 722b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (intent.hasExtra(MediaStore.EXTRA_VIDEO_QUALITY)) { 723b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project int extraVideoQuality = intent.getIntExtra(MediaStore.EXTRA_VIDEO_QUALITY, 0); 724b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project videoQualityHigh = (extraVideoQuality > 0); 725b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 726b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 727b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // Use the same frame rate for both, since internally 728b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // if the frame rate is too large, it can cause camera to become 729b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // unstable. We need to fix the MediaRecorder to disable the support 730b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // of setting frame rate for now. 731b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mMediaRecorder.setVideoFrameRate(20); 732b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (videoQualityHigh) { 733b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mMediaRecorder.setVideoSize(352,288); 734b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } else { 735b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mMediaRecorder.setVideoSize(176,144); 736b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 737b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mMediaRecorder.setVideoEncoder(MediaRecorder.VideoEncoder.H263); 738b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (!DEBUG_SUPPRESS_AUDIO_RECORDING) { 739b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mMediaRecorder.setAudioEncoder(MediaRecorder.AudioEncoder.AMR_NB); 740b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 741b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mMediaRecorder.setPreviewDisplay(mSurfaceHolder.getSurface()); 742de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project 743de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project long remaining = getAvailableStorage(); 744de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project // remaining >= LOW_STORAGE_THRESHOLD at this point, reserve a quarter 745de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project // of that to make it more likely that recording can complete successfully. 746de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project try { 747de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project mMediaRecorder.setMaxFileSize(remaining - LOW_STORAGE_THRESHOLD / 4); 748de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project } catch (RuntimeException exception) { 749de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project // We are going to ignore failure of setMaxFileSize here, as 750de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project // a) The composer selected may simply not support it, or 751de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project // b) The underlying media framework may not handle 64-bit range 752de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project // on the size restriction. 753de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project } 754de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project 755b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project try { 756b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mMediaRecorder.prepare(); 757b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } catch (IOException exception) { 758b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Log.e(TAG, "prepare failed for " + mCameraVideoFilename); 759b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project releaseMediaRecorder(); 760b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // TODO: add more exception handling logic here 761b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return false; 762b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 763b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mMediaRecorderRecording = false; 7649bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang 7659bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang if (!mIsVideoCaptureIntent && !mThumbController.isUriValid()) { 7669bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang updateLastVideo(); 7679bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang } 7689bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang 7699bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang if (!mIsVideoCaptureIntent) { 7709bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang mThumbController.updateDisplayIfNeeded(); 7719bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang } 7729bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang 773b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return true; 774b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 775b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 776b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private void releaseMediaRecorder() { 777b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Log.v(TAG, "Releasing media recorder."); 778b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (mMediaRecorder != null) { 779b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project cleanupEmptyFile(); 780b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mMediaRecorder.reset(); 781b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mMediaRecorder.release(); 782b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mMediaRecorder = null; 783b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 784b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 785b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 786b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private int getIntPreference(String key, int defaultValue) { 787b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project String s = mPreferences.getString(key, ""); 788b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project int result = defaultValue; 789b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project try { 790b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project result = Integer.parseInt(s); 791b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } catch (NumberFormatException e) { 792b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // Ignore, result is already the default value. 793b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 794b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return result; 795b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 796b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 797b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private boolean getBooleanPreference(String key, boolean defaultValue) { 798b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return getIntPreference(key, defaultValue ? 1 : 0) != 0; 799b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 800b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 801b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private void createVideoPath() { 802b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project long dateTaken = System.currentTimeMillis(); 803b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project String title = createName(dateTaken); 804b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project String displayName = title + ".3gp"; // Used when emailing. 805b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project String cameraDirPath = ImageManager.CAMERA_IMAGE_BUCKET_NAME; 806b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project File cameraDir = new File(cameraDirPath); 807b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project cameraDir.mkdirs(); 808b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project SimpleDateFormat dateFormat = new SimpleDateFormat( 809b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project getString(R.string.video_file_name_format)); 810b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Date date = new Date(dateTaken); 811b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project String filepart = dateFormat.format(date); 812b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project String filename = cameraDirPath + "/" + filepart + ".3gp"; 813b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project ContentValues values = new ContentValues(7); 814b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project values.put(Video.Media.TITLE, title); 815b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project values.put(Video.Media.DISPLAY_NAME, displayName); 816b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project values.put(Video.Media.DESCRIPTION, ""); 817b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project values.put(Video.Media.DATE_TAKEN, dateTaken); 818b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project values.put(Video.Media.MIME_TYPE, "video/3gpp"); 819b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project values.put(Video.Media.DATA, filename); 820b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mCameraVideoFilename = filename; 821b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Log.v(TAG, "Current camera video filename: " + mCameraVideoFilename); 822b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mCurrentVideoValues = values; 823b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 824b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 825b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private void registerVideo() { 826b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (mCameraVideoFileDescriptor == null) { 827b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Uri videoTable = Uri.parse("content://media/external/video/media"); 828b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mCurrentVideoUri = mContentResolver.insert(videoTable, 829b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mCurrentVideoValues); 830b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Log.v(TAG, "Current video URI: " + mCurrentVideoUri); 831b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 832b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mCurrentVideoValues = null; 833b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 834b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 835b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private void deleteCurrentVideo() { 836b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (mCurrentVideoFilename != null) { 837b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project deleteVideoFile(mCurrentVideoFilename); 838b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mCurrentVideoFilename = null; 839b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 840b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (mCurrentVideoUri != null) { 841b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mContentResolver.delete(mCurrentVideoUri, null, null); 842b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mCurrentVideoUri = null; 843b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 844de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project updateAndShowStorageHint(true); 845b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 846b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 847b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private void deleteVideoFile(String fileName) { 848b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Log.v(TAG, "Deleting video " + fileName); 849b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project File f = new File(fileName); 850b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (! f.delete()) { 851b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Log.v(TAG, "Could not delete " + fileName); 852b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 853b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 854b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 855b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private void addBaseMenuItems(Menu menu) { 856b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project MenuHelper.addSwitchModeMenuItem(menu, this, false); 857b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project { 858b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project MenuItem gallery = menu.add(MenuHelper.IMAGE_MODE_ITEM, MENU_GALLERY_PHOTOS, 0, R.string.camera_gallery_photos_text).setOnMenuItemClickListener(new OnMenuItemClickListener() { 859b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public boolean onMenuItemClick(MenuItem item) { 860b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project gotoGallery(); 861b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return true; 862b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 863b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project }); 864b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project gallery.setIcon(android.R.drawable.ic_menu_gallery); 865b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mGalleryItems.add(gallery); 866b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 867b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project { 868b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project MenuItem gallery = menu.add(MenuHelper.VIDEO_MODE_ITEM, MENU_GALLERY_VIDEOS, 0, R.string.camera_gallery_photos_text).setOnMenuItemClickListener(new OnMenuItemClickListener() { 869b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public boolean onMenuItemClick(MenuItem item) { 870b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project gotoGallery(); 871b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return true; 872b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 873b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project }); 874b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project gallery.setIcon(android.R.drawable.ic_menu_gallery); 875b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mGalleryItems.add(gallery); 876b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 877b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 878b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project MenuItem item = menu.add(MenuHelper.GENERIC_ITEM, MENU_SETTINGS, 0, R.string.settings).setOnMenuItemClickListener(new OnMenuItemClickListener() { 879b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public boolean onMenuItemClick(MenuItem item) { 880b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Intent intent = new Intent(); 881b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project intent.setClass(VideoCamera.this, CameraSettings.class); 882b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project startActivity(intent); 883b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return true; 884b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 885b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project }); 886b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project item.setIcon(android.R.drawable.ic_menu_preferences); 887b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 888b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 889b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // from MediaRecorder.OnErrorListener 890b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project public void onError(MediaRecorder mr, int what, int extra) { 891b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (what == MediaRecorder.MEDIA_RECORDER_ERROR_UNKNOWN) { 892b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // We may have run out of space on the sdcard. 893b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project stopVideoRecording(); 8949a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project updateAndShowStorageHint(true); 895b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 896b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 897b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 8988d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project // from MediaRecorder.OnInfoListener 8998d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project public void onInfo(MediaRecorder mr, int what, int extra) { 9008d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project if (what == MediaRecorder.MEDIA_RECORDER_INFO_MAX_DURATION_REACHED) { 901de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project mShutterButton.performClick(); 902de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project } else if (what == MediaRecorder.MEDIA_RECORDER_INFO_MAX_FILESIZE_REACHED) { 903de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project mShutterButton.performClick(); 904de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project updateAndShowStorageHint(true); 9058d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project } 9068d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project } 9078d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project 9089c9be2eb4a86fc3468dbba1ec5f7bfdb37d22c74The Android Open Source Project /* 9099c9be2eb4a86fc3468dbba1ec5f7bfdb37d22c74The Android Open Source Project * Make sure we're not recording music playing in the background, ask 9109c9be2eb4a86fc3468dbba1ec5f7bfdb37d22c74The Android Open Source Project * the MediaPlaybackService to pause playback. 9119c9be2eb4a86fc3468dbba1ec5f7bfdb37d22c74The Android Open Source Project */ 9129c9be2eb4a86fc3468dbba1ec5f7bfdb37d22c74The Android Open Source Project private void pauseAudioPlayback() { 9139c9be2eb4a86fc3468dbba1ec5f7bfdb37d22c74The Android Open Source Project // Shamelessly copied from MediaPlaybackService.java, which 9149c9be2eb4a86fc3468dbba1ec5f7bfdb37d22c74The Android Open Source Project // should be public, but isn't. 9159c9be2eb4a86fc3468dbba1ec5f7bfdb37d22c74The Android Open Source Project Intent i = new Intent("com.android.music.musicservicecommand"); 9169c9be2eb4a86fc3468dbba1ec5f7bfdb37d22c74The Android Open Source Project i.putExtra("command", "pause"); 9179c9be2eb4a86fc3468dbba1ec5f7bfdb37d22c74The Android Open Source Project 9189c9be2eb4a86fc3468dbba1ec5f7bfdb37d22c74The Android Open Source Project sendBroadcast(i); 9199c9be2eb4a86fc3468dbba1ec5f7bfdb37d22c74The Android Open Source Project } 9209c9be2eb4a86fc3468dbba1ec5f7bfdb37d22c74The Android Open Source Project 921b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private void startVideoRecording() { 922b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Log.v(TAG, "startVideoRecording"); 923b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (!mMediaRecorderRecording) { 924b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 9259a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project if (mStorageStatus != STORAGE_STATUS_OK) { 926b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Log.v(TAG, "Storage issue, ignore the start request"); 927b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return; 928b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 929b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 930b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project // Check mMediaRecorder to see whether it is initialized or not. 931b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (mMediaRecorder == null && initializeVideo() == false ) { 932b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Log.e(TAG, "Initialize video (MediaRecorder) failed."); 933b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return; 934b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 935b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 9369c9be2eb4a86fc3468dbba1ec5f7bfdb37d22c74The Android Open Source Project pauseAudioPlayback(); 9379c9be2eb4a86fc3468dbba1ec5f7bfdb37d22c74The Android Open Source Project 938b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project try { 939b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mMediaRecorder.setOnErrorListener(this); 9408d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project mMediaRecorder.setOnInfoListener(this); 941b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mMediaRecorder.start(); // Recording is now started 942b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } catch (RuntimeException e) { 943b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Log.e(TAG, "Could not start media recorder. ", e); 944b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return; 945b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 946b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mMediaRecorderRecording = true; 947b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mRecordingStartTime = SystemClock.uptimeMillis(); 948b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project updateRecordingIndicator(true); 949b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mRecordingTimeView.setText(""); 950b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mRecordingTimeView.setVisibility(View.VISIBLE); 951b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mHandler.sendEmptyMessage(UPDATE_RECORD_TIME); 952b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project setScreenTimeoutInfinite(); 953de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project hideLastPictureButton(); 954b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 955b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 956b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 957b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private void updateRecordingIndicator(boolean showRecording) { 958b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project int drawableId = showRecording ? R.drawable.ic_camera_bar_indicator_record 959b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project : R.drawable.ic_camera_indicator_video; 960b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Drawable drawable = getResources().getDrawable(drawableId); 961b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mShutterButton.setImageDrawable(drawable); 962b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 963b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 9649bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang private void stopVideoRecordingAndGetThumbnail() { 9659bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang stopVideoRecording(); 9669bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang acquireVideoThumb(); 967b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 968b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 969de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project private void stopVideoRecordingAndShowAlert() { 970de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project stopVideoRecording(); 9719bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang showAlert(); 972de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project } 973de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project 9749bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang private void showAlert() { 975b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project int[] pickIds = {R.id.attach, R.id.cancel}; 976b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project int[] normalIds = {R.id.gallery, R.id.share, R.id.discard}; 977b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project int[] alwaysOnIds = {R.id.play}; 978b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project int[] hideIds = pickIds; 979b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project int[] connectIds = normalIds; 9809bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang if (mIsVideoCaptureIntent) { 981b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project hideIds = normalIds; 982b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project connectIds = pickIds; 983b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 984b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project for(int id : hideIds) { 985b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mPostPictureAlert.findViewById(id).setVisibility(View.GONE); 986b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 9878d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project ActionMenuButton shareButton = 9888d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project (ActionMenuButton) mPostPictureAlert.findViewById(R.id.share); 9898d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project shareButton.setRestricted( 9908d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project mCurrentVideoFileLength > SHARE_FILE_LENGTH_LIMIT); 991b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project connectAndFadeIn(connectIds); 992b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project connectAndFadeIn(alwaysOnIds); 993de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project hideLastPictureButton(); 994b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mPostPictureAlert.setVisibility(View.VISIBLE); 9959bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang 9969bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang // There are two cases we are here: 9979bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang // (1) We are in a capture video intent, and we are reviewing the video 9989bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang // we just taken. 9999bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang // (2) The thumbnail button is clicked: we review the video associated 10009bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang // with the thumbnail. 10019bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang // For the second case, we copy the associated URI and filename to 10029bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang // mCurrentVideoUri and mCurrentVideoFilename, so the video frame shown 10039bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang // and the target for actions (play, delete, ...) will be correct. 10049bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang 10059bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang if (!mIsVideoCaptureIntent) { 10069bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang mCurrentVideoUri = mThumbController.getUri(); 10079bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang mCurrentVideoFilename = getDataPath(mCurrentVideoUri); 10089bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang } 10099bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang 10109bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang String path = mCurrentVideoFilename; 10119bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang if (path != null) { 10129bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang Bitmap videoFrame = ImageManager.createVideoThumbnail(path); 10139bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang mVideoFrame.setImageBitmap(videoFrame); 10149bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang mVideoFrame.setVisibility(View.VISIBLE); 10159bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang } 1016b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 1017b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 10189bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang private void hideAlert() { 1019de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project mVideoFrame.setVisibility(View.INVISIBLE); 1020de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project mPostPictureAlert.setVisibility(View.INVISIBLE); 1021de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project showLastPictureButton(); 1022de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project } 1023de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project 1024b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private void connectAndFadeIn(int[] connectIds) { 1025b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project for(int id : connectIds) { 1026b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project View view = mPostPictureAlert.findViewById(id); 1027b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project view.setOnClickListener(this); 1028b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Animation animation = new AlphaAnimation(0F, 1F); 1029b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project animation.setDuration(500); 10309bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang view.startAnimation(animation); 1031b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 1032b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 1033b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 10349bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang private boolean isAlertVisible() { 1035b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project return mPostPictureAlert.getVisibility() == View.VISIBLE; 1036b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 1037b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 1038b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private void stopVideoRecording() { 1039b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Log.v(TAG, "stopVideoRecording"); 1040b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project boolean needToRegisterRecording = false; 1041b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (mMediaRecorderRecording || mMediaRecorder != null) { 1042b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if (mMediaRecorderRecording && mMediaRecorder != null) { 1043b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project try { 1044b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mMediaRecorder.setOnErrorListener(null); 10458d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project mMediaRecorder.setOnInfoListener(null); 1046b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mMediaRecorder.stop(); 1047b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } catch (RuntimeException e) { 1048b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Log.e(TAG, "stop fail: " + e.getMessage()); 1049b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 10508d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project 1051b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mCurrentVideoFilename = mCameraVideoFilename; 10528d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project try { 10538d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project mCurrentVideoFileLength = new File(mCurrentVideoFilename).length(); 10548d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project } catch (RuntimeException e) { 10558d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project Log.e(TAG, "get file length fail: " + e.getMessage()); 10568d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project mCurrentVideoFileLength = 0; 10578d0dd0e2ee9a9f8d729ed96597102777cf14701fThe Android Open Source Project } 1058b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Log.v(TAG, "Setting current video filename: " + mCurrentVideoFilename); 1059b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project needToRegisterRecording = true; 1060b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mMediaRecorderRecording = false; 1061b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 1062b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project releaseMediaRecorder(); 1063b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project updateRecordingIndicator(false); 1064b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mRecordingTimeView.setVisibility(View.GONE); 1065b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project setScreenTimeoutLong(); 1066b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 10679a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project if (needToRegisterRecording && mStorageStatus == STORAGE_STATUS_OK) { 10689a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project registerVideo(); 10699a379bd668227d3dcea30312025f304fd248f6e3The Android Open Source Project } 1070b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 1071b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mCameraVideoFilename = null; 1072b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mCameraVideoFileDescriptor = null; 1073b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 1074b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 1075b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private void setScreenTimeoutSystemDefault() { 1076b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mHandler.removeMessages(CLEAR_SCREEN_DELAY); 1077b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project clearScreenOnFlag(); 1078b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 1079b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 1080b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private void setScreenTimeoutLong() { 1081b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mHandler.removeMessages(CLEAR_SCREEN_DELAY); 1082b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project setScreenOnFlag(); 1083b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mHandler.sendEmptyMessageDelayed(CLEAR_SCREEN_DELAY, SCREEN_DELAY); 1084b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 1085b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 1086b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private void setScreenTimeoutInfinite() { 1087b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project mHandler.removeMessages(CLEAR_SCREEN_DELAY); 1088b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project setScreenOnFlag(); 1089b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 1090b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 1091b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private void clearScreenOnFlag() { 1092b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Window w = getWindow(); 1093b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project final int keepScreenOnFlag = WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON; 1094b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if ((w.getAttributes().flags & keepScreenOnFlag) != 0) { 1095b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project w.clearFlags(keepScreenOnFlag); 1096b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 1097b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 1098b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 1099b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project private void setScreenOnFlag() { 1100b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project Window w = getWindow(); 1101b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project final int keepScreenOnFlag = WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON; 1102b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project if ((w.getAttributes().flags & keepScreenOnFlag) == 0) { 1103b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project w.addFlags(keepScreenOnFlag); 1104b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 1105b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 1106b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 11079bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang private void hideAlertAndStartPreview() { 11089bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang hideAlert(); 11099bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang initializeVideo(); 1110b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 1111b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 11129bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang private void hideAlertAndStartVideoRecording() { 11139bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang hideAlert(); 11149bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang startVideoRecording(); 1115b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 1116b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 11179bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang private void acquireVideoThumb() { 11189bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang Bitmap videoFrame = ImageManager.createVideoThumbnail(mCurrentVideoFilename); 11199bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang mThumbController.setData(mCurrentVideoUri, videoFrame); 1120de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project } 1121de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project 11229bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang private void showLastPictureButton() { 11239bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang if (!mIsVideoCaptureIntent) { 11249bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang mLastPictureButton.setVisibility(View.VISIBLE); 1125de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project } 11269bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang } 1127de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project 11289bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang private void hideLastPictureButton() { 11299bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang if (!mIsVideoCaptureIntent) { 11309bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang mLastPictureButton.setVisibility(View.INVISIBLE); 11319bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang } 1132de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project } 1133de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project 11349bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang private static ImageManager.DataLocation dataLocation() { 11359bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang return ImageManager.DataLocation.EXTERNAL; 1136de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project } 1137de365d87520c97d6b1636442e6b5c82a3e036f29The Android Open Source Project 11389bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang private void updateLastVideo() { 11399bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang ImageManager.IImageList list = ImageManager.instance().allImages( 11409bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang this, 11419bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang mContentResolver, 11429bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang dataLocation(), 11439bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang ImageManager.INCLUDE_VIDEOS, 11449bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang ImageManager.SORT_ASCENDING, 11459bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang ImageManager.CAMERA_IMAGE_BUCKET_ID); 11469bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang int count = list.getCount(); 11479bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang if (count > 0) { 11489bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang ImageManager.IImage image = list.getImageAt(count-1); 11499bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang Uri uri = image.fullSizeImageUri(); 11509bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang mThumbController.setData(uri, image.miniThumbBitmap()); 11519bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang } else { 11529bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang mThumbController.setData(null, null); 11539bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang } 11549bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang list.deactivate(); 1155b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 1156b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project 11579bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang private static final String[] DATA_PATH_PROJECTION = new String[] { 11589bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang "_data" 11599bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang }; 11609bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang 11619bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang private String getDataPath(Uri uri) { 11629bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang Cursor c = null; 11639bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang try { 11649bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang c = mContentResolver.query(uri, DATA_PATH_PROJECTION, null, null, null); 11659bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang if (c != null && c.moveToFirst()) { 11669bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang return c.getString(0); 11679bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang } else { 11689bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang return null; 11699bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang } 11709bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang } finally { 11719bc8d1b47e5bab978cc9571ddfdedc8309a0b65dChih-Chung Chang if (c != null) c.close(); 1172b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 1173b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project } 1174b64d345c9d51cabce43b5191532a0c185d2a70a5The Android Open Source Project} 1175