mirror of
https://git.code.sf.net/p/opencamera/code.git
synced 2024-09-19 19:42:29 +02:00
Smoother zoom for Camera2 API - both more zoom entries, and supporting smooth zoom for pinch zoom.
This commit is contained in:
parent
c42ac38fc5
commit
a041de3ef1
@ -61,6 +61,7 @@ FIXED Long pressing on the shutter button in video mode meant nothing happened
|
||||
ADDED Camera vendor extensions show percentage progress on supported Android 14 devices.
|
||||
ADDED Long press on switch camera icons now bring up a menu to jump to any camera (for devices
|
||||
that expose multiple cameras).
|
||||
UPDATED Smoother zoom for Camera2 API.
|
||||
UPDATED Improvements for loading thumbnails for gallery icon (including fixing orientation for
|
||||
X-NIGHT portrait images on Pixel 6 Pro).
|
||||
UPDATED Improvements for popup menu and exposure UI when using large font sizes.
|
||||
|
@ -5479,7 +5479,9 @@ public class MainActivity extends AppCompatActivity implements PreferenceFragmen
|
||||
Log.d(TAG, "zoom onProgressChanged: " + progress);
|
||||
// note we zoom even if !fromUser, as various other UI controls (multitouch, volume key zoom, -/+ zoomcontrol)
|
||||
// indirectly set zoom via this method, from setting the zoom slider
|
||||
preview.zoomTo(preview.getMaxZoom() - progress);
|
||||
// if hasSmoothZoom()==true, then the preview already handled zooming to the current value
|
||||
if( !preview.hasSmoothZoom() )
|
||||
preview.zoomTo(preview.getMaxZoom() - progress, false);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -60,7 +60,7 @@ public abstract class CameraController {
|
||||
public static class CameraFeatures {
|
||||
public boolean is_zoom_supported;
|
||||
public int max_zoom;
|
||||
public List<Integer> zoom_ratios;
|
||||
public List<Integer> zoom_ratios; // list of supported zoom ratios; each value is the zoom multiplied by 100
|
||||
public boolean supports_face_detection;
|
||||
public List<CameraController.Size> picture_sizes;
|
||||
public List<CameraController.Size> video_sizes;
|
||||
@ -541,8 +541,25 @@ public abstract class CameraController {
|
||||
public abstract TonemapProfile getTonemapProfile();
|
||||
public abstract int getJpegQuality();
|
||||
public abstract void setJpegQuality(int quality);
|
||||
/** Returns the current zoom. The returned value is an index into the CameraFeatures.zoom_ratios
|
||||
* array.
|
||||
*/
|
||||
public abstract int getZoom();
|
||||
/** Set the zoom.
|
||||
* @param value The index into the CameraFeatures.zoom_ratios array.
|
||||
*/
|
||||
public abstract void setZoom(int value);
|
||||
/** Set the zoom. Unlike setZoom(value), this allows specifying any zoom level within the
|
||||
* supported range.
|
||||
* @param value The index into the CameraFeatures.zoom_ratios array.
|
||||
* @param smooth_zoom The desired zoom. With CameraController1 (old Camera API), this is ignored.
|
||||
* With CameraController2 (Camera2 API), this is used instead of the zoom_ratios
|
||||
* value. Note that getZoom() will return the value passed to this method, so
|
||||
* passing an appropriate value (e.g., whatever zoom_ratio is closest to the
|
||||
* smooth_zoom) is still useful if you want to make use of getZoom().
|
||||
* smooth_zoom must still be within the supported range of zoom values.
|
||||
*/
|
||||
public abstract void setZoom(int value, float smooth_zoom);
|
||||
public abstract void resetZoom(); // resets to zoom 1x
|
||||
public abstract int getExposureCompensation();
|
||||
public abstract boolean setExposureCompensation(int new_exposure);
|
||||
|
@ -963,6 +963,11 @@ public class CameraController1 extends CameraController {
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setZoom(int value, float smooth_zoom) {
|
||||
setZoom(value);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void resetZoom() {
|
||||
setZoom(0);
|
||||
|
@ -2514,12 +2514,12 @@ public class CameraController2 extends CameraController {
|
||||
int zoom_value_1x;
|
||||
|
||||
// prepare zoom rations > 1x
|
||||
// set 20 steps per 2x factor
|
||||
final double scale_factor_c = 1.0352649238413775043477881942112;
|
||||
// set 40 steps per 2x factor
|
||||
final double scale_factor_c = 1.0174796921026863936352862847966;
|
||||
List<Integer> zoom_ratios_above_one = new ArrayList<>();
|
||||
double zoom = scale_factor_c;
|
||||
while( zoom < max_zoom - 1.0e-5f ) {
|
||||
int zoom_ratio = (int)(zoom*100);
|
||||
int zoom_ratio = (int)(zoom*100+1.0e-5);
|
||||
zoom_ratios_above_one.add(zoom_ratio);
|
||||
zoom *= scale_factor_c;
|
||||
}
|
||||
@ -4801,6 +4801,11 @@ public class CameraController2 extends CameraController {
|
||||
|
||||
@Override
|
||||
public void setZoom(int value) {
|
||||
setZoom(value, -1.0f);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setZoom(int value, float smooth_zoom) {
|
||||
if( zoom_ratios == null ) {
|
||||
if( MyDebug.LOG )
|
||||
Log.d(TAG, "zoom not supported");
|
||||
@ -4821,7 +4826,21 @@ public class CameraController2 extends CameraController {
|
||||
Log.e(TAG, "invalid zoom value" + value);
|
||||
throw new RuntimeException(); // throw as RuntimeException, as this is a programming error
|
||||
}
|
||||
float zoom = zoom_ratios.get(value)/100.0f;
|
||||
if( smooth_zoom > 0.0f ) {
|
||||
if( smooth_zoom < zoom_ratios.get(0)/100.0f ) {
|
||||
if( MyDebug.LOG )
|
||||
Log.e(TAG, "invalid smooth_zoom: " + smooth_zoom);
|
||||
throw new RuntimeException("smooth_zoom too small");
|
||||
}
|
||||
else if( smooth_zoom > zoom_ratios.get(zoom_ratios.size()-1)/100.0f ) {
|
||||
if( MyDebug.LOG )
|
||||
Log.e(TAG, "invalid smooth_zoom: " + smooth_zoom);
|
||||
throw new RuntimeException("smooth_zoom too large");
|
||||
}
|
||||
}
|
||||
float zoom = smooth_zoom > 0.0f ? smooth_zoom : zoom_ratios.get(value)/100.0f;
|
||||
if( MyDebug.LOG )
|
||||
Log.d(TAG, "zoom to: " + zoom);
|
||||
|
||||
if( Build.VERSION.SDK_INT >= Build.VERSION_CODES.R ) {
|
||||
camera_settings.has_control_zoom_ratio = true;
|
||||
|
@ -761,6 +761,13 @@ public class Preview implements SurfaceHolder.Callback, TextureView.SurfaceTextu
|
||||
private boolean has_smooth_zoom = false;
|
||||
private float smooth_zoom = 1.0f;
|
||||
|
||||
/** Returns true if the user is currently pinch zooming, and the Preview has already handled setting
|
||||
* the zoom via Preview.zoomTo().
|
||||
*/
|
||||
public boolean hasSmoothZoom() {
|
||||
return this.has_smooth_zoom;
|
||||
}
|
||||
|
||||
/** Handle multitouch zoom.
|
||||
*/
|
||||
private class ScaleListener extends ScaleGestureDetector.SimpleOnScaleGestureListener {
|
||||
@ -821,7 +828,7 @@ public class Preview implements SurfaceHolder.Callback, TextureView.SurfaceTextu
|
||||
if( MyDebug.LOG )
|
||||
Log.d(TAG, "snapped pinch zoom to 1x zoom");
|
||||
int snapped_zoom = find1xZoom();
|
||||
zoomTo(snapped_zoom);
|
||||
zoomTo(snapped_zoom, false);
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -2208,7 +2215,7 @@ public class Preview implements SurfaceHolder.Callback, TextureView.SurfaceTextu
|
||||
if( zoom_pref == -1 ) {
|
||||
zoom_pref = find1xZoom();
|
||||
}
|
||||
zoomTo(zoom_pref);
|
||||
zoomTo(zoom_pref, false);
|
||||
if( MyDebug.LOG ) {
|
||||
Log.d(TAG, "setupCamera: total time after zoomTo: " + (System.currentTimeMillis() - debug_time));
|
||||
}
|
||||
@ -4303,7 +4310,9 @@ public class Preview implements SurfaceHolder.Callback, TextureView.SurfaceTextu
|
||||
Log.d(TAG, "scaleZoom() " + scale_factor);
|
||||
if( this.camera_controller != null && this.has_zoom ) {
|
||||
int new_zoom_factor = getScaledZoomFactor(scale_factor);
|
||||
// n.b., don't call zoomTo; this should be called indirectly by applicationInterface.multitouchZoom()
|
||||
if( has_smooth_zoom )
|
||||
zoomTo(new_zoom_factor, true);
|
||||
// else don't call zoomTo; this should be called indirectly by applicationInterface.multitouchZoom()
|
||||
applicationInterface.multitouchZoom(new_zoom_factor);
|
||||
}
|
||||
}
|
||||
@ -4311,7 +4320,7 @@ public class Preview implements SurfaceHolder.Callback, TextureView.SurfaceTextu
|
||||
/** Zooms to the supplied index (within the zoom_ratios array).
|
||||
* @param new_zoom_factor The index to zoom to.
|
||||
*/
|
||||
public void zoomTo(int new_zoom_factor) {
|
||||
public void zoomTo(int new_zoom_factor, boolean allow_smooth_zoom) {
|
||||
if( MyDebug.LOG )
|
||||
Log.d(TAG, "ZoomTo(): " + new_zoom_factor);
|
||||
if( new_zoom_factor < 0 )
|
||||
@ -4322,7 +4331,9 @@ public class Preview implements SurfaceHolder.Callback, TextureView.SurfaceTextu
|
||||
if( camera_controller != null ) {
|
||||
if( this.has_zoom ) {
|
||||
// don't cancelAutoFocus() here, otherwise we get sluggish zoom behaviour on Camera2 API
|
||||
camera_controller.setZoom(new_zoom_factor);
|
||||
// if pinch zooming, pass through the "smooth" zoom factor so for Camera2 API we get perfectly smooth zoom, rather than it
|
||||
// being snapped to the discrete zoom values
|
||||
camera_controller.setZoom(new_zoom_factor, (allow_smooth_zoom && has_smooth_zoom) ? smooth_zoom : -1.0f);
|
||||
applicationInterface.setZoomPref(new_zoom_factor);
|
||||
clearFocusAreas();
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user