1d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd/* 2d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd * Copyright (C) 2015 The Android Open Source Project 3d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd * 4d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd * Licensed under the Apache License, Version 2.0 (the "License"); 5d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd * you may not use this file except in compliance with the License. 6d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd * You may obtain a copy of the License at 7d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd * 8d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd * http://www.apache.org/licenses/LICENSE-2.0 9d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd * 10d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd * Unless required by applicable law or agreed to in writing, software 11d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd * distributed under the License is distributed on an "AS IS" BASIS, 12d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd * See the License for the specific language governing permissions and 14d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd * limitations under the License. 15d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd */ 16d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 17d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddpackage com.android.messaging.ui.mediapicker; 18d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 19d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddimport android.Manifest; 20d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddimport android.content.Context; 21d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddimport android.content.pm.PackageManager; 22d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddimport android.graphics.Rect; 23d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddimport android.hardware.Camera; 24d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddimport android.net.Uri; 25d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddimport android.os.SystemClock; 26d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddimport android.view.LayoutInflater; 27d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddimport android.view.MotionEvent; 28d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddimport android.view.View; 29d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddimport android.view.ViewGroup; 30d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddimport android.view.animation.AlphaAnimation; 31d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddimport android.view.animation.Animation; 32d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddimport android.view.animation.AnimationSet; 33d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddimport android.widget.Chronometer; 34d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddimport android.widget.ImageButton; 35d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 36d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddimport com.android.messaging.R; 37d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddimport com.android.messaging.datamodel.data.MediaPickerMessagePartData; 38d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddimport com.android.messaging.ui.mediapicker.CameraManager.MediaCallback; 39d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddimport com.android.messaging.ui.mediapicker.camerafocus.RenderOverlay; 40d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddimport com.android.messaging.util.Assert; 41d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddimport com.android.messaging.util.LogUtil; 42d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddimport com.android.messaging.util.OsUtil; 43d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddimport com.android.messaging.util.UiUtils; 44d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 45d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd/** 46d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd * Chooser which allows the user to take pictures or video without leaving the current app/activity 47d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd */ 48d3b009ae55651f1e60950342468e3c37fdeb0796Mike Doddclass CameraMediaChooser extends MediaChooser implements 49d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd CameraManager.CameraManagerListener { 50d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd private CameraPreview.CameraPreviewHost mCameraPreviewHost; 51d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd private ImageButton mFullScreenButton; 52d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd private ImageButton mSwapCameraButton; 53d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd private ImageButton mSwapModeButton; 54d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd private ImageButton mCaptureButton; 55d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd private ImageButton mCancelVideoButton; 56d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd private Chronometer mVideoCounter; 57d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd private boolean mVideoCancelled; 58d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd private int mErrorToast; 59d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd private View mEnabledView; 60d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd private View mMissingPermissionView; 61d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 62d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd CameraMediaChooser(final MediaPicker mediaPicker) { 63d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd super(mediaPicker); 64d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 65d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 66d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 67d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd public int getSupportedMediaTypes() { 68d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd if (CameraManager.get().hasAnyCamera()) { 69d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd return MediaPicker.MEDIA_TYPE_IMAGE | MediaPicker.MEDIA_TYPE_VIDEO; 70d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } else { 71d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd return MediaPicker.MEDIA_TYPE_NONE; 72d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 73d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 74d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 75d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 76d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd public View destroyView() { 77d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd CameraManager.get().closeCamera(); 78d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd CameraManager.get().setListener(null); 79d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd CameraManager.get().setSubscriptionDataProvider(null); 80d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd return super.destroyView(); 81d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 82d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 83d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 84d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd protected View createView(final ViewGroup container) { 85d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd CameraManager.get().setListener(this); 86d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd CameraManager.get().setSubscriptionDataProvider(this); 87d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd CameraManager.get().setVideoMode(false); 88d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd final LayoutInflater inflater = getLayoutInflater(); 89d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd final CameraMediaChooserView view = (CameraMediaChooserView) inflater.inflate( 90d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd R.layout.mediapicker_camera_chooser, 91d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd container /* root */, 92d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd false /* attachToRoot */); 93d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mCameraPreviewHost = (CameraPreview.CameraPreviewHost) view.findViewById( 94d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd R.id.camera_preview); 95d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mCameraPreviewHost.getView().setOnTouchListener(new View.OnTouchListener() { 96d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 97d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd public boolean onTouch(final View view, final MotionEvent motionEvent) { 98d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd if (CameraManager.get().isVideoMode()) { 99d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd // Prevent the swipe down in video mode because video is always captured in 100d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd // full screen 101d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd return true; 102d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 103d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 104d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd return false; 105d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 106d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd }); 107d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 108d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd final View shutterVisual = view.findViewById(R.id.camera_shutter_visual); 109d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 110d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mFullScreenButton = (ImageButton) view.findViewById(R.id.camera_fullScreen_button); 111d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mFullScreenButton.setOnClickListener(new View.OnClickListener() { 112d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 113d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd public void onClick(final View view) { 114d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mMediaPicker.setFullScreen(true); 115d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 116d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd }); 117d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 118d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mSwapCameraButton = (ImageButton) view.findViewById(R.id.camera_swapCamera_button); 119d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mSwapCameraButton.setOnClickListener(new View.OnClickListener() { 120d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 121d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd public void onClick(final View view) { 122d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd CameraManager.get().swapCamera(); 123d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 124d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd }); 125d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 126d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mCaptureButton = (ImageButton) view.findViewById(R.id.camera_capture_button); 127d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mCaptureButton.setOnClickListener(new View.OnClickListener() { 128d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 129d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd public void onClick(final View v) { 130d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd final float heightPercent = Math.min(mMediaPicker.getViewPager().getHeight() / 131d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd (float) mCameraPreviewHost.getView().getHeight(), 1); 132d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 133d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd if (CameraManager.get().isRecording()) { 134d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd CameraManager.get().stopVideo(); 135d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } else { 136d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd final CameraManager.MediaCallback callback = new CameraManager.MediaCallback() { 137d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 138d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd public void onMediaReady( 139d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd final Uri uriToVideo, final String contentType, 140d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd final int width, final int height) { 141d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mVideoCounter.stop(); 142d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd if (mVideoCancelled || uriToVideo == null) { 143d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mVideoCancelled = false; 144d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } else { 145d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd final Rect startRect = new Rect(); 146d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd // It's possible to throw out the chooser while taking the 147d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd // picture/video. In that case, still use the attachment, just 148d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd // skip the startRect 149d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd if (mView != null) { 150d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mView.getGlobalVisibleRect(startRect); 151d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 152d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mMediaPicker.dispatchItemsSelected( 153d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd new MediaPickerMessagePartData(startRect, contentType, 154d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd uriToVideo, width, height), 155d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd true /* dismissMediaPicker */); 156d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 157d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd updateViewState(); 158d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 159d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 160d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 161d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd public void onMediaFailed(final Exception exception) { 162d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd UiUtils.showToastAtBottom(R.string.camera_media_failure); 163d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd updateViewState(); 164d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 165d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 166d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 167d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd public void onMediaInfo(final int what) { 168d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd if (what == MediaCallback.MEDIA_NO_DATA) { 169d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd UiUtils.showToastAtBottom(R.string.camera_media_failure); 170d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 171d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd updateViewState(); 172d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 173d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd }; 174d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd if (CameraManager.get().isVideoMode()) { 175d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd CameraManager.get().startVideo(callback); 176d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mVideoCounter.setBase(SystemClock.elapsedRealtime()); 177d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mVideoCounter.start(); 178d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd updateViewState(); 179d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } else { 180d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd showShutterEffect(shutterVisual); 181d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd CameraManager.get().takePicture(heightPercent, callback); 182d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd updateViewState(); 183d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 184d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 185d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 186d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd }); 187d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 188d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mSwapModeButton = (ImageButton) view.findViewById(R.id.camera_swap_mode_button); 189d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mSwapModeButton.setOnClickListener(new View.OnClickListener() { 190d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 191d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd public void onClick(final View view) { 192d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd final boolean isSwitchingToVideo = !CameraManager.get().isVideoMode(); 193d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd if (isSwitchingToVideo && !OsUtil.hasRecordAudioPermission()) { 194d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd requestRecordAudioPermission(); 195d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } else { 196d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd onSwapMode(); 197d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 198d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 199d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd }); 200d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 201d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mCancelVideoButton = (ImageButton) view.findViewById(R.id.camera_cancel_button); 202d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mCancelVideoButton.setOnClickListener(new View.OnClickListener() { 203d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 204d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd public void onClick(final View view) { 205d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mVideoCancelled = true; 206d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd CameraManager.get().stopVideo(); 207d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mMediaPicker.dismiss(true); 208d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 209d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd }); 210d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 211d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mVideoCounter = (Chronometer) view.findViewById(R.id.camera_video_counter); 212d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 213d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd CameraManager.get().setRenderOverlay((RenderOverlay) view.findViewById(R.id.focus_visual)); 214d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 215d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mEnabledView = view.findViewById(R.id.mediapicker_enabled); 216d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mMissingPermissionView = view.findViewById(R.id.missing_permission_view); 217d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 218d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd // Must set mView before calling updateViewState because it operates on mView 219d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mView = view; 220d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd updateViewState(); 221d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd updateForPermissionState(CameraManager.hasCameraPermission()); 222d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd return view; 223d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 224d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 225d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 226d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd public int getIconResource() { 227d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd return R.drawable.ic_camera_light; 228d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 229d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 230d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 231d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd public int getIconDescriptionResource() { 232d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd return R.string.mediapicker_cameraChooserDescription; 233d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 234d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 235d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd /** 236d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd * Updates the view when entering or leaving full-screen camera mode 237d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd * @param fullScreen 238d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd */ 239d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 240d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd void onFullScreenChanged(final boolean fullScreen) { 241d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd super.onFullScreenChanged(fullScreen); 242d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd if (!fullScreen && CameraManager.get().isVideoMode()) { 243d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd CameraManager.get().setVideoMode(false); 244d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 245d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd updateViewState(); 246d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 247d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 248d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd /** 249d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd * Initializes the control to a default state when it is opened / closed 250d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd * @param open True if the control is opened 251d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd */ 252d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 253d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd void onOpenedChanged(final boolean open) { 254d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd super.onOpenedChanged(open); 255d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd updateViewState(); 256d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 257d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 258d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 259d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd protected void setSelected(final boolean selected) { 260d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd super.setSelected(selected); 261d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd if (selected) { 262d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd if (CameraManager.hasCameraPermission()) { 263d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd // If an error occurred before the chooser was selected, show it now 264d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd showErrorToastIfNeeded(); 265d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } else { 266d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd requestCameraPermission(); 267d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 268d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 269d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 270d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 271d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd private void requestCameraPermission() { 272d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mMediaPicker.requestPermissions(new String[] { Manifest.permission.CAMERA }, 273d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd MediaPicker.CAMERA_PERMISSION_REQUEST_CODE); 274d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 275d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 276d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd private void requestRecordAudioPermission() { 277d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mMediaPicker.requestPermissions(new String[] { Manifest.permission.RECORD_AUDIO }, 278d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd MediaPicker.RECORD_AUDIO_PERMISSION_REQUEST_CODE); 279d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 280d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 281d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 282d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd protected void onRequestPermissionsResult( 283d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd final int requestCode, final String permissions[], final int[] grantResults) { 284d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd if (requestCode == MediaPicker.CAMERA_PERMISSION_REQUEST_CODE) { 285d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd final boolean permissionGranted = grantResults[0] == PackageManager.PERMISSION_GRANTED; 286d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd updateForPermissionState(permissionGranted); 287d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd if (permissionGranted) { 288d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mCameraPreviewHost.onCameraPermissionGranted(); 289d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 290d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } else if (requestCode == MediaPicker.RECORD_AUDIO_PERMISSION_REQUEST_CODE) { 291d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd Assert.isFalse(CameraManager.get().isVideoMode()); 292d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd if (grantResults[0] == PackageManager.PERMISSION_GRANTED) { 293d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd // Switch to video mode 294d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd onSwapMode(); 295d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } else { 296d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd // Stay in still-photo mode 297d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 298d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 299d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 300d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 301d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd private void updateForPermissionState(final boolean granted) { 302d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd // onRequestPermissionsResult can sometimes get called before createView(). 303d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd if (mEnabledView == null) { 304d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd return; 305d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 306d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 307d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mEnabledView.setVisibility(granted ? View.VISIBLE : View.GONE); 308d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mMissingPermissionView.setVisibility(granted ? View.GONE : View.VISIBLE); 309d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 310d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 311d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 312d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd public boolean canSwipeDown() { 313d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd if (CameraManager.get().isVideoMode()) { 314d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd return true; 315d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 316d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd return super.canSwipeDown(); 317d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 318d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 319d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd /** 320d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd * Handles an error from the camera manager by showing the appropriate error message to the user 321d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd * @param errorCode One of the CameraManager.ERROR_* constants 322d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd * @param e The exception which caused the error, if any 323d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd */ 324d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 325d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd public void onCameraError(final int errorCode, final Exception e) { 326d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd switch (errorCode) { 327d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd case CameraManager.ERROR_OPENING_CAMERA: 328d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd case CameraManager.ERROR_SHOWING_PREVIEW: 329d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mErrorToast = R.string.camera_error_opening; 330d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd break; 331d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd case CameraManager.ERROR_INITIALIZING_VIDEO: 332d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mErrorToast = R.string.camera_error_video_init_fail; 333d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd updateViewState(); 334d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd break; 335d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd case CameraManager.ERROR_STORAGE_FAILURE: 336d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mErrorToast = R.string.camera_error_storage_fail; 337d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd updateViewState(); 338d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd break; 339d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd case CameraManager.ERROR_TAKING_PICTURE: 340d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mErrorToast = R.string.camera_error_failure_taking_picture; 341d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd break; 342d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd default: 343d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mErrorToast = R.string.camera_error_unknown; 344d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd LogUtil.w(LogUtil.BUGLE_TAG, "Unknown camera error:" + errorCode); 345d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd break; 346d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 347d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd showErrorToastIfNeeded(); 348d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 349d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 350d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd private void showErrorToastIfNeeded() { 351d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd if (mErrorToast != 0 && mSelected) { 352d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd UiUtils.showToastAtBottom(mErrorToast); 353d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mErrorToast = 0; 354d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 355d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 356d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 357d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 358d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd public void onCameraChanged() { 359d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd updateViewState(); 360d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 361d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 362d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd private void onSwapMode() { 363d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd CameraManager.get().setVideoMode(!CameraManager.get().isVideoMode()); 364d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd if (CameraManager.get().isVideoMode()) { 365d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mMediaPicker.setFullScreen(true); 366d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 367d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd // For now we start recording immediately 368d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mCaptureButton.performClick(); 369d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 370d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd updateViewState(); 371d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 372d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 373d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd private void showShutterEffect(final View shutterVisual) { 374d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd final float maxAlpha = getContext().getResources().getFraction( 375d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd R.fraction.camera_shutter_max_alpha, 1 /* base */, 1 /* pBase */); 376d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 377d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd // Divide by 2 so each half of the animation adds up to the full duration 378d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd final int animationDuration = getContext().getResources().getInteger( 379d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd R.integer.camera_shutter_duration) / 2; 380d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 381d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd final AnimationSet animation = new AnimationSet(false /* shareInterpolator */); 382d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd final Animation alphaInAnimation = new AlphaAnimation(0.0f, maxAlpha); 383d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd alphaInAnimation.setDuration(animationDuration); 384d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd animation.addAnimation(alphaInAnimation); 385d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 386d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd final Animation alphaOutAnimation = new AlphaAnimation(maxAlpha, 0.0f); 387d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd alphaOutAnimation.setStartOffset(animationDuration); 388d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd alphaOutAnimation.setDuration(animationDuration); 389d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd animation.addAnimation(alphaOutAnimation); 390d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 391d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd animation.setAnimationListener(new Animation.AnimationListener() { 392d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 393d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd public void onAnimationStart(final Animation animation) { 394d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd shutterVisual.setVisibility(View.VISIBLE); 395d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 396d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 397d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 398d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd public void onAnimationEnd(final Animation animation) { 399d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd shutterVisual.setVisibility(View.GONE); 400d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 401d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 402d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 403d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd public void onAnimationRepeat(final Animation animation) { 404d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 405d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd }); 406d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd shutterVisual.startAnimation(animation); 407d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 408d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 409d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd /** Updates the state of the buttons and overlays based on the current state of the view */ 410d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd private void updateViewState() { 411d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd if (mView == null) { 412d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd return; 413d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 414d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 415d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd final Context context = getContext(); 416d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd if (context == null) { 417d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd // Context is null if the fragment was already removed from the activity 418d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd return; 419d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 420d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd final boolean fullScreen = mMediaPicker.isFullScreen(); 421d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd final boolean videoMode = CameraManager.get().isVideoMode(); 422d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd final boolean isRecording = CameraManager.get().isRecording(); 423d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd final boolean isCameraAvailable = isCameraAvailable(); 424d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd final Camera.CameraInfo cameraInfo = CameraManager.get().getCameraInfo(); 425d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd final boolean frontCamera = cameraInfo != null && cameraInfo.facing == 426d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd Camera.CameraInfo.CAMERA_FACING_FRONT; 427d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 428d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mView.setSystemUiVisibility( 429d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd fullScreen ? View.SYSTEM_UI_FLAG_LOW_PROFILE : 430d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd View.SYSTEM_UI_FLAG_VISIBLE); 431d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 432d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mFullScreenButton.setVisibility(!fullScreen ? View.VISIBLE : View.GONE); 433d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mFullScreenButton.setEnabled(isCameraAvailable); 434d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mSwapCameraButton.setVisibility( 435d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd fullScreen && !isRecording && CameraManager.get().hasFrontAndBackCamera() ? 436d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd View.VISIBLE : View.GONE); 437d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mSwapCameraButton.setImageResource(frontCamera ? 438d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd R.drawable.ic_camera_front_light : 439d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd R.drawable.ic_camera_rear_light); 440d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mSwapCameraButton.setEnabled(isCameraAvailable); 441d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 442d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mCancelVideoButton.setVisibility(isRecording ? View.VISIBLE : View.GONE); 443d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mVideoCounter.setVisibility(isRecording ? View.VISIBLE : View.GONE); 444d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 445d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mSwapModeButton.setImageResource(videoMode ? 446d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd R.drawable.ic_mp_camera_small_light : 447d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd R.drawable.ic_mp_video_small_light); 448d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mSwapModeButton.setContentDescription(context.getString(videoMode ? 449d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd R.string.camera_switch_to_still_mode : R.string.camera_switch_to_video_mode)); 450d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mSwapModeButton.setVisibility(isRecording ? View.GONE : View.VISIBLE); 451d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mSwapModeButton.setEnabled(isCameraAvailable); 452d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 453d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd if (isRecording) { 454d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mCaptureButton.setImageResource(R.drawable.ic_mp_capture_stop_large_light); 455d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mCaptureButton.setContentDescription(context.getString( 456d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd R.string.camera_stop_recording)); 457d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } else if (videoMode) { 458d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mCaptureButton.setImageResource(R.drawable.ic_mp_video_large_light); 459d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mCaptureButton.setContentDescription(context.getString( 460d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd R.string.camera_start_recording)); 461d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } else { 462d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mCaptureButton.setImageResource(R.drawable.ic_checkmark_large_light); 463d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mCaptureButton.setContentDescription(context.getString( 464d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd R.string.camera_take_picture)); 465d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 466d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd mCaptureButton.setEnabled(isCameraAvailable); 467d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 468d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 469d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd @Override 470d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd int getActionBarTitleResId() { 471d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd return 0; 472d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 473d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd 474d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd /** 475d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd * Returns if the camera is currently ready camera is loaded and not taking a picture. 476d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd * otherwise we should avoid taking another picture, swapping camera or recording video. 477d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd */ 478d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd private boolean isCameraAvailable() { 479d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd return CameraManager.get().isCameraAvailable(); 480d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd } 481d3b009ae55651f1e60950342468e3c37fdeb0796Mike Dodd} 482