public class

SensorOrientedMeteringPointFactory

extends MeteringPointFactory

 java.lang.Object

androidx.camera.core.MeteringPointFactory

↳androidx.camera.core.SensorOrientedMeteringPointFactory

Overview

A MeteringPointFactory that can create MeteringPoint by sensor oriented x, y , width and height.

This factory is suitable for apps that already have coordinates translated into sensor coordinates. It is also useful for apps that want to focus on something detected in ImageAnalysis. Apps can pass the ImageAnalysis instance for useCaseForFOV argument and CameraX will then adjust the final sensor coordinates by aspect ratio of ImageAnalysis.

Summary

Constructors
publicSensorOrientedMeteringPointFactory(float width, float height)

Creates the SensorOrientedMeteringPointFactory by width and height

publicSensorOrientedMeteringPointFactory(float width, float height, UseCase useCaseForFOV)

Creates the SensorOrientedMeteringPointFactory by width, height and useCaseForFOV.

Methods
protected PointFtranslatePoint(float x, float y)

from MeteringPointFactoryconvertPoint, createPoint, createPoint, getDefaultPointSize
from java.lang.Objectclone, equals, finalize, getClass, hashCode, notify, notifyAll, toString, wait, wait, wait

Constructors

public SensorOrientedMeteringPointFactory(float width, float height)

Creates the SensorOrientedMeteringPointFactory by width and height

The width/height is the logical width/height of the preview FoV in sensor orientation and X/Y is the logical XY inside the FOV. User can set the width and height to 1.0 which will make the XY the normalized coordinates [0..1].

By default, it will use active Preview as the FoV for final coordinates translation.

Parameters:

width: the logical width of FoV in sensor orientation
height: the logical height of FoV in sensor orientation

public SensorOrientedMeteringPointFactory(float width, float height, UseCase useCaseForFOV)

Creates the SensorOrientedMeteringPointFactory by width, height and useCaseForFOV.

The width/height is the logical width/height of the preview FoV in sensor orientation and X/Y is the logical XY inside the FOV. User can set the width and height to 1.0 which will make the XY the normalized coordinates [0..1].

useCaseForFOV is used to determine the FOV of this translation. This useCaseForFOV needs to be bound via CameraX first. Otherwise it will throw a java.lang.IllegalStateException

Parameters:

width: the logical width of FOV in sensor orientation.
height: the logical height of FOV in sensor orientation.
useCaseForFOV: the UseCase to be the FOV.

Methods

protected PointF translatePoint(float x, float y)

Source

/*
 * Copyright 2019 The Android Open Source Project
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package androidx.camera.core;

import android.graphics.PointF;
import android.util.Rational;
import android.util.Size;

import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.lifecycle.LifecycleOwner;

import java.util.Set;

/**
 * A {@link MeteringPointFactory} that can create {@link MeteringPoint} by sensor oriented x, y ,
 * width and height.
 *
 * <p>This factory is suitable for apps that already have coordinates translated into sensor
 * coordinates. It is also useful for apps that want to focus on something detected in
 * {@link ImageAnalysis}. Apps can pass the {@link ImageAnalysis} instance for useCaseForFOV
 * argument and CameraX will then adjust the final sensor coordinates by aspect ratio of
 * ImageAnalysis.
 */
public class SensorOrientedMeteringPointFactory extends MeteringPointFactory {
    /** the logical width of FoV in sensor orientation*/
    private final float mWidth;
    /** the logical height of FoV in sensor orientation */
    private final float mHeight;

    /**
     * Creates the SensorOrientedMeteringPointFactory by width and height
     *
     * <p>The width/height is the logical width/height of the preview FoV in sensor orientation and
     * X/Y is the logical XY inside the FOV. User can set the width and height to 1.0 which will
     * make the XY the normalized coordinates [0..1].
     *
     * <p>By default, it will use active {@link Preview} as the FoV for final coordinates
     * translation.
     *
     * @param width the logical width of FoV in sensor orientation
     * @param height the logical height of FoV in sensor orientation
     */
    public SensorOrientedMeteringPointFactory(float width, float height) {
        mWidth = width;
        mHeight = height;
        mFOVAspectRatio = null;
    }

    /**
     * Creates the SensorOrientedMeteringPointFactory by width, height and useCaseForFOV.
     *
     * <p>The width/height is the logical width/height of the preview FoV in sensor orientation and
     * X/Y is the logical XY inside the FOV. User can set the width and height to 1.0 which will
     * make the XY the normalized coordinates [0..1].
     *
     * <p>useCaseForFOV is used to determine the FOV of this translation. This useCaseForFOV needs
     * to be bound via {@link CameraX#bindToLifecycle(LifecycleOwner, UseCase...)} first. Otherwise
     * it will throw a {@link IllegalStateException}
     *
     * @param width the logical width of FOV in sensor orientation.
     * @param height the logical height of FOV in sensor orientation.
     * @param useCaseForFOV the {@link UseCase} to be the FOV.
     */
    public SensorOrientedMeteringPointFactory(float width, float height,
            @NonNull UseCase useCaseForFOV) {
        mWidth = width;
        mHeight = height;
        mFOVAspectRatio = getUseCaseAspectRatio(useCaseForFOV);
    }

    @Nullable
    private Rational getUseCaseAspectRatio(@Nullable UseCase useCase) {
        if (useCase == null) {
            return null;
        }

        Set<String> cameraIds = useCase.getAttachedCameraIds();
        if (cameraIds.isEmpty()) {
            throw new IllegalStateException("UseCase " + useCase + " is not bound.");
        }

        for (String id : cameraIds) {
            Size resolution = useCase.getAttachedSurfaceResolution(id);
            // Returns an aspect ratio of first found attachedSurfaceResolution.
            return new Rational(resolution.getWidth(), resolution.getHeight());
        }

        return null;
    }

    /**
     * {@inheritDoc}
     */
    @Override
    @NonNull
    protected PointF translatePoint(float x, float y) {
        PointF pt = new PointF(x / mWidth, y / mHeight);
        return pt;
    }

}