fix false camera captures

// FREEBIE
This commit is contained in:
Jake McGinty 2015-11-23 15:19:05 -08:00 committed by Moxie Marlinspike
parent 3a5d4e7ebe
commit b4e28e219b
5 changed files with 74 additions and 24 deletions

View File

@ -14,6 +14,7 @@
android:layout_centerHorizontal="true"
android:background="@drawable/quick_camera_shutter_ring"
android:src="@drawable/quick_shutter_button"
android:enabled="false"
android:padding="20dp"/>
<ImageButton android:id="@+id/fullscreen_button"
@ -21,7 +22,7 @@
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
android:layout_alignParentRight="true"
android:background="#00000000"
android:background="@drawable/circle_touch_highlight_background"
android:src="@drawable/quick_camera_fullscreen"
android:padding="20dp" />
@ -30,8 +31,9 @@
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
android:layout_alignParentLeft="true"
android:background="#00000000"
android:background="@drawable/circle_touch_highlight_background"
android:src="@drawable/quick_camera_rear"
android:enabled="false"
android:padding="20dp"
android:visibility="invisible"
tools:visibility="visible" />

View File

@ -14,6 +14,7 @@
android:layout_centerVertical="true"
android:background="@drawable/quick_camera_shutter_ring"
android:src="@drawable/quick_shutter_button"
android:enabled="false"
android:padding="20dp"/>
<ImageButton android:id="@+id/fullscreen_button"
@ -21,7 +22,7 @@
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
android:layout_alignParentRight="true"
android:background="#00000000"
android:background="@drawable/circle_touch_highlight_background"
android:src="@drawable/quick_camera_fullscreen"
android:padding="20dp"/>
@ -30,8 +31,9 @@
android:layout_height="wrap_content"
android:layout_alignParentTop="true"
android:layout_alignParentRight="true"
android:background="#00000000"
android:background="@drawable/circle_touch_highlight_background"
android:src="@drawable/quick_camera_rear"
android:enabled="false"
android:padding="20dp"
android:visibility="invisible"
tools:visibility="visible"/>

View File

@ -1362,6 +1362,12 @@ public class ConversationActivity extends PassphraseRequiredActionBarActivity
quickAttachmentToggle.disable();
}
@Override
public void onCameraStart() {}
@Override
public void onCameraStop() {}
@Override
public void onRecorderStarted() {
Vibrator vibrator = (Vibrator)getSystemService(Context.VIBRATOR_SERVICE);

View File

@ -37,6 +37,8 @@ import android.view.OrientationEventListener;
import android.view.ViewGroup;
import java.io.IOException;
import java.util.Collections;
import java.util.LinkedList;
import java.util.List;
import org.thoughtcrime.securesms.ApplicationContext;
@ -61,7 +63,7 @@ public class CameraView extends ViewGroup {
private @NonNull State state = State.PAUSED;
private @Nullable Size previewSize;
private @Nullable CameraViewListener listener;
private @NonNull List<CameraViewListener> listeners = Collections.synchronizedList(new LinkedList<CameraViewListener>());
private int outputOrientation = -1;
public CameraView(Context context) {
@ -102,7 +104,9 @@ public class CameraView extends ViewGroup {
@Nullable
Void onRunBackground() {
try {
long openStartMillis = System.currentTimeMillis();
camera = Optional.fromNullable(Camera.open(cameraId));
Log.w(TAG, "camera.open() -> " + (System.currentTimeMillis() - openStartMillis) + "ms");
synchronized (CameraView.this) {
CameraView.this.notifyAll();
}
@ -117,7 +121,9 @@ public class CameraView extends ViewGroup {
protected void onPostMain(Void avoid) {
if (!camera.isPresent()) {
Log.w(TAG, "tried to open camera but got null");
if (listener != null) listener.onCameraFail();
for (CameraViewListener listener : listeners) {
listener.onCameraFail();
}
return;
}
@ -167,6 +173,10 @@ public class CameraView extends ViewGroup {
Log.w(TAG, "onPause() completed");
}
});
for (CameraViewListener listener : listeners) {
listener.onCameraStop();
}
}
public boolean isStarted() {
@ -215,8 +225,8 @@ public class CameraView extends ViewGroup {
if (camera.isPresent()) startPreview(camera.get().getParameters());
}
public void setListener(@Nullable CameraViewListener listener) {
this.listener = listener;
public void addListener(@NonNull CameraViewListener listener) {
listeners.add(listener);
}
public void setPreviewCallback(final @NonNull PreviewCallback previewCallback) {
@ -308,9 +318,19 @@ public class CameraView extends ViewGroup {
} else {
previewSize = parameters.getPreviewSize();
}
long previewStartMillis = System.currentTimeMillis();
camera.startPreview();
postRequestLayout();
Log.w(TAG, "camera.startPreview() -> " + (System.currentTimeMillis() - previewStartMillis) + "ms");
state = State.ACTIVE;
Util.runOnMain(new Runnable() {
@Override
public void run() {
requestLayout();
for (CameraViewListener listener : listeners) {
listener.onCameraStart();
}
}
});
} catch (Exception e) {
Log.w(TAG, e);
}
@ -328,6 +348,7 @@ public class CameraView extends ViewGroup {
}
}
private Size getPreferredPreviewSize(@NonNull Parameters parameters) {
return CameraUtils.getPreferredPreviewSize(displayOrientation,
getMeasuredWidth(),
@ -349,15 +370,6 @@ public class CameraView extends ViewGroup {
return outputOrientation;
}
private void postRequestLayout() {
post(new Runnable() {
@Override
public void run() {
requestLayout();
}
});
}
private @NonNull CameraInfo getCameraInfo() {
final CameraInfo info = new Camera.CameraInfo();
Camera.getCameraInfo(cameraId, info);
@ -553,7 +565,11 @@ public class CameraView extends ViewGroup {
@Override
protected void onPostExecute(byte[] imageBytes) {
if (imageBytes != null && listener != null) listener.onImageCapture(imageBytes);
if (imageBytes != null) {
for (CameraViewListener listener : listeners) {
listener.onImageCapture(imageBytes);
}
}
}
}
@ -562,6 +578,8 @@ public class CameraView extends ViewGroup {
public interface CameraViewListener {
void onImageCapture(@NonNull final byte[] imageBytes);
void onCameraFail();
void onCameraStart();
void onCameraStop();
}
public interface PreviewCallback {

View File

@ -31,7 +31,7 @@ import org.thoughtcrime.securesms.util.ServiceUtil;
import org.thoughtcrime.securesms.util.Util;
import org.thoughtcrime.securesms.util.ViewUtil;
public class QuickAttachmentDrawer extends ViewGroup implements InputView {
public class QuickAttachmentDrawer extends ViewGroup implements InputView, CameraViewListener {
private static final String TAG = QuickAttachmentDrawer.class.getSimpleName();
private final ViewDragHelper dragHelper;
@ -80,6 +80,7 @@ public class QuickAttachmentDrawer extends ViewGroup implements InputView {
coverViewPosition = getChildCount();
controls.setVisibility(GONE);
cameraView.setVisibility(GONE);
cameraView.addListener(this);
}
public static boolean isDeviceSupported(Context context) {
@ -337,7 +338,28 @@ public class QuickAttachmentDrawer extends ViewGroup implements InputView {
public void setListener(AttachmentDrawerListener listener) {
this.listener = listener;
if (cameraView != null) cameraView.setListener(listener);
cameraView.addListener(listener);
}
@Override
public void onImageCapture(@NonNull byte[] imageBytes) {}
@Override
public void onCameraFail() {
swapCameraButton.setEnabled(false);
shutterButton.setEnabled(false);
}
@Override
public void onCameraStart() {
swapCameraButton.setEnabled(true);
shutterButton.setEnabled(true);
}
@Override
public void onCameraStop() {
swapCameraButton.setEnabled(false);
shutterButton.setEnabled(false);
}
public interface AttachmentDrawerListener extends CameraViewListener {