Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 7cf7ebd0 authored by Lajos Molnar's avatar Lajos Molnar Committed by Automerger Merge Worker
Browse files

Merge "media: add EncoderProfiles" into sc-dev am: 02643234

Original change: https://googleplex-android-review.googlesource.com/c/platform/frameworks/base/+/13924167

Change-Id: I6ba9e5d1b7a928ce2ef23a785d73acfbf85b03b0
parents f4e1e672 02643234
Loading
Loading
Loading
Loading
+29 −0
Original line number Original line Diff line number Diff line
@@ -20898,6 +20898,7 @@ package android.media {
  public class CamcorderProfile {
  public class CamcorderProfile {
    method public static android.media.CamcorderProfile get(int);
    method public static android.media.CamcorderProfile get(int);
    method public static android.media.CamcorderProfile get(int, int);
    method public static android.media.CamcorderProfile get(int, int);
    method @Nullable public static android.media.EncoderProfiles getAll(@NonNull String, int);
    method public static boolean hasProfile(int);
    method public static boolean hasProfile(int);
    method public static boolean hasProfile(int, int);
    method public static boolean hasProfile(int, int);
    field public static final int QUALITY_1080P = 6; // 0x6
    field public static final int QUALITY_1080P = 6; // 0x6
@@ -20978,6 +20979,32 @@ package android.media {
    field @NonNull public final java.util.UUID uuid;
    field @NonNull public final java.util.UUID uuid;
  }
  }
  public class EncoderProfiles {
    method @NonNull public java.util.List<android.media.EncoderProfiles.AudioProfile> getAudioProfiles();
    method public int getDurationSeconds();
    method public int getFileFormat();
    method @NonNull public java.util.List<android.media.EncoderProfiles.VideoProfile> getVideoProfiles();
  }
  public static class EncoderProfiles.AudioProfile {
    method public int getBitrate();
    method public int getChannels();
    method public int getCodec();
    method @NonNull public String getMediaType();
    method public int getProfile();
    method public int getSampleRate();
  }
  public static class EncoderProfiles.VideoProfile {
    method public int getBitrate();
    method public int getCodec();
    method public int getFrameRate();
    method public int getHeight();
    method @NonNull public String getMediaType();
    method public int getProfile();
    method public int getWidth();
  }
  public class ExifInterface {
  public class ExifInterface {
    ctor public ExifInterface(@NonNull java.io.File) throws java.io.IOException;
    ctor public ExifInterface(@NonNull java.io.File) throws java.io.IOException;
    ctor public ExifInterface(@NonNull String) throws java.io.IOException;
    ctor public ExifInterface(@NonNull String) throws java.io.IOException;
@@ -22904,6 +22931,7 @@ package android.media {
    method public void setAudioChannels(int);
    method public void setAudioChannels(int);
    method public void setAudioEncoder(int) throws java.lang.IllegalStateException;
    method public void setAudioEncoder(int) throws java.lang.IllegalStateException;
    method public void setAudioEncodingBitRate(int);
    method public void setAudioEncodingBitRate(int);
    method public void setAudioProfile(@NonNull android.media.EncoderProfiles.AudioProfile);
    method public void setAudioSamplingRate(int);
    method public void setAudioSamplingRate(int);
    method public void setAudioSource(int) throws java.lang.IllegalStateException;
    method public void setAudioSource(int) throws java.lang.IllegalStateException;
    method @Deprecated public void setCamera(android.hardware.Camera);
    method @Deprecated public void setCamera(android.hardware.Camera);
@@ -22932,6 +22960,7 @@ package android.media {
    method public void setVideoEncodingBitRate(int);
    method public void setVideoEncodingBitRate(int);
    method public void setVideoEncodingProfileLevel(int, int);
    method public void setVideoEncodingProfileLevel(int, int);
    method public void setVideoFrameRate(int) throws java.lang.IllegalStateException;
    method public void setVideoFrameRate(int) throws java.lang.IllegalStateException;
    method public void setVideoProfile(@NonNull android.media.EncoderProfiles.VideoProfile);
    method public void setVideoSize(int, int) throws java.lang.IllegalStateException;
    method public void setVideoSize(int, int) throws java.lang.IllegalStateException;
    method public void setVideoSource(int) throws java.lang.IllegalStateException;
    method public void setVideoSource(int) throws java.lang.IllegalStateException;
    method public void start() throws java.lang.IllegalStateException;
    method public void start() throws java.lang.IllegalStateException;
+171 −7
Original line number Original line Diff line number Diff line
@@ -16,6 +16,9 @@


package android.media;
package android.media;


import android.annotation.IntDef;
import android.annotation.NonNull;
import android.annotation.Nullable;
import android.compat.annotation.UnsupportedAppUsage;
import android.compat.annotation.UnsupportedAppUsage;
import android.hardware.Camera;
import android.hardware.Camera;
import android.hardware.Camera.CameraInfo;
import android.hardware.Camera.CameraInfo;
@@ -23,6 +26,9 @@ import android.hardware.camera2.CameraManager;
import android.hardware.camera2.CameraMetadata;
import android.hardware.camera2.CameraMetadata;
import android.os.Build;
import android.os.Build;


import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;

/**
/**
 * Retrieves the
 * Retrieves the
 * predefined camcorder profile settings for camcorder applications.
 * predefined camcorder profile settings for camcorder applications.
@@ -275,6 +281,53 @@ public class CamcorderProfile
    private static final int QUALITY_HIGH_SPEED_LIST_START = QUALITY_HIGH_SPEED_LOW;
    private static final int QUALITY_HIGH_SPEED_LIST_START = QUALITY_HIGH_SPEED_LOW;
    private static final int QUALITY_HIGH_SPEED_LIST_END = QUALITY_HIGH_SPEED_4KDCI;
    private static final int QUALITY_HIGH_SPEED_LIST_END = QUALITY_HIGH_SPEED_4KDCI;


    /**
     * @hide
     */
    @IntDef({
        QUALITY_LOW,
        QUALITY_HIGH,
        QUALITY_QCIF,
        QUALITY_CIF,
        QUALITY_480P,
        QUALITY_720P,
        QUALITY_1080P,
        QUALITY_QVGA,
        QUALITY_2160P,
        QUALITY_VGA,
        QUALITY_4KDCI,
        QUALITY_QHD,
        QUALITY_2K,
        QUALITY_8KUHD,

        QUALITY_TIME_LAPSE_LOW ,
        QUALITY_TIME_LAPSE_HIGH,
        QUALITY_TIME_LAPSE_QCIF,
        QUALITY_TIME_LAPSE_CIF,
        QUALITY_TIME_LAPSE_480P,
        QUALITY_TIME_LAPSE_720P,
        QUALITY_TIME_LAPSE_1080P,
        QUALITY_TIME_LAPSE_QVGA,
        QUALITY_TIME_LAPSE_2160P,
        QUALITY_TIME_LAPSE_VGA,
        QUALITY_TIME_LAPSE_4KDCI,
        QUALITY_TIME_LAPSE_QHD,
        QUALITY_TIME_LAPSE_2K,
        QUALITY_TIME_LAPSE_8KUHD,

        QUALITY_HIGH_SPEED_LOW,
        QUALITY_HIGH_SPEED_HIGH,
        QUALITY_HIGH_SPEED_480P,
        QUALITY_HIGH_SPEED_720P,
        QUALITY_HIGH_SPEED_1080P,
        QUALITY_HIGH_SPEED_2160P,
        QUALITY_HIGH_SPEED_CIF,
        QUALITY_HIGH_SPEED_VGA,
        QUALITY_HIGH_SPEED_4KDCI,
    })
    @Retention(RetentionPolicy.SOURCE)
    public @interface Quality {}

    /**
    /**
     * Default recording duration in seconds before the session is terminated.
     * Default recording duration in seconds before the session is terminated.
     * This is useful for applications like MMS has limited file size requirement.
     * This is useful for applications like MMS has limited file size requirement.
@@ -385,9 +438,8 @@ public class CamcorderProfile
    public int audioChannels;
    public int audioChannels;


    /**
    /**
     * Returns the camcorder profile for the first back-facing camera on the
     * Returns the default camcorder profile at the given quality level for the first back-facing
     * device at the given quality level. If the device has no back-facing
     * camera on the device. If the device has no back-facing camera, this returns null.
     * camera, this returns null.
     * @param quality the target quality level for the camcorder profile
     * @param quality the target quality level for the camcorder profile
     * @see #get(int, int)
     * @see #get(int, int)
     */
     */
@@ -404,8 +456,7 @@ public class CamcorderProfile
    }
    }


    /**
    /**
     * Returns the camcorder profile for the given camera at the given
     * Returns the default camcorder profile for the given camera at the given quality level.
     * quality level.
     *
     *
     * Quality levels QUALITY_LOW, QUALITY_HIGH are guaranteed to be supported, while
     * Quality levels QUALITY_LOW, QUALITY_HIGH are guaranteed to be supported, while
     * other levels may or may not be supported. The supported levels can be checked using
     * other levels may or may not be supported. The supported levels can be checked using
@@ -457,6 +508,7 @@ public class CamcorderProfile
     * @see #QUALITY_HIGH_SPEED_720P
     * @see #QUALITY_HIGH_SPEED_720P
     * @see #QUALITY_HIGH_SPEED_1080P
     * @see #QUALITY_HIGH_SPEED_1080P
     * @see #QUALITY_HIGH_SPEED_2160P
     * @see #QUALITY_HIGH_SPEED_2160P
     * @throws IllegalArgumentException if quality is not one of the defined QUALITY_ values.
    */
    */
    public static CamcorderProfile get(int cameraId, int quality) {
    public static CamcorderProfile get(int cameraId, int quality) {
        if (!((quality >= QUALITY_LIST_START &&
        if (!((quality >= QUALITY_LIST_START &&
@@ -472,7 +524,119 @@ public class CamcorderProfile
    }
    }


    /**
    /**
     * Returns true if camcorder profile exists for the first back-facing
     * Returns all encoder profiles of a camcorder profile for the given camera at
     * the given quality level.
     *
     * Quality levels QUALITY_LOW, QUALITY_HIGH are guaranteed to be supported, while
     * other levels may or may not be supported. The supported levels can be checked using
     * {@link #hasProfile(int, int)}.
     * QUALITY_LOW refers to the lowest quality available, while QUALITY_HIGH refers to
     * the highest quality available.
     * QUALITY_LOW/QUALITY_HIGH have to match one of qcif, cif, 480p, 720p, 1080p or 2160p.
     * E.g. if the device supports 480p, 720p, 1080p and 2160p, then low is 480p and high is
     * 2160p.
     *
     * The same is true for time lapse quality levels, i.e. QUALITY_TIME_LAPSE_LOW,
     * QUALITY_TIME_LAPSE_HIGH are guaranteed to be supported and have to match one of
     * qcif, cif, 480p, 720p, 1080p, or 2160p.
     *
     * For high speed quality levels, they may or may not be supported. If a subset of the levels
     * are supported, QUALITY_HIGH_SPEED_LOW and QUALITY_HIGH_SPEED_HIGH are guaranteed to be
     * supported and have to match one of 480p, 720p, or 1080p.
     *
     * A camcorder recording session with higher quality level usually has higher output
     * bit rate, better video and/or audio recording quality, larger video frame
     * resolution and higher audio sampling rate, etc, than those with lower quality
     * level.
     *
     * @param cameraId the id for the camera. Numeric camera ids parsed from the list received by
     *                 invoking {@link CameraManager#getCameraIdList} can be used as long as they
     *                 are {@link CameraMetadata#REQUEST_AVAILABLE_CAPABILITIES_BACKWARD_COMPATIBLE}
     *                 and not
     *                 {@link CameraMetadata#INFO_SUPPORTED_HARDWARE_LEVEL_EXTERNAL EXTERNAL}.
     * @param quality the target quality level for the camcorder profile.
     * @return null if there are no encoder profiles defined for the quality level for the
     * given camera.
     * @throws IllegalArgumentException if quality is not one of the defined QUALITY_ values.
     * @see #QUALITY_LOW
     * @see #QUALITY_HIGH
     * @see #QUALITY_QCIF
     * @see #QUALITY_CIF
     * @see #QUALITY_480P
     * @see #QUALITY_720P
     * @see #QUALITY_1080P
     * @see #QUALITY_2160P
     * @see #QUALITY_TIME_LAPSE_LOW
     * @see #QUALITY_TIME_LAPSE_HIGH
     * @see #QUALITY_TIME_LAPSE_QCIF
     * @see #QUALITY_TIME_LAPSE_CIF
     * @see #QUALITY_TIME_LAPSE_480P
     * @see #QUALITY_TIME_LAPSE_720P
     * @see #QUALITY_TIME_LAPSE_1080P
     * @see #QUALITY_TIME_LAPSE_2160P
     * @see #QUALITY_HIGH_SPEED_LOW
     * @see #QUALITY_HIGH_SPEED_HIGH
     * @see #QUALITY_HIGH_SPEED_480P
     * @see #QUALITY_HIGH_SPEED_720P
     * @see #QUALITY_HIGH_SPEED_1080P
     * @see #QUALITY_HIGH_SPEED_2160P
    */
    @Nullable public static EncoderProfiles getAll(
            @NonNull String cameraId, @Quality int quality) {
        if (!((quality >= QUALITY_LIST_START &&
               quality <= QUALITY_LIST_END) ||
              (quality >= QUALITY_TIME_LAPSE_LIST_START &&
               quality <= QUALITY_TIME_LAPSE_LIST_END) ||
               (quality >= QUALITY_HIGH_SPEED_LIST_START &&
               quality <= QUALITY_HIGH_SPEED_LIST_END))) {
            String errMessage = "Unsupported quality level: " + quality;
            throw new IllegalArgumentException(errMessage);
        }

        // TODO: get all profiles
        int id;
        try {
            id = Integer.valueOf(cameraId);
        } catch (NumberFormatException e) {
            return null;
        }
        CamcorderProfile cp = native_get_camcorder_profile(id, quality);
        if (cp == null) {
            return null;
        };

        EncoderProfiles.AudioProfile[] audioProfiles;
        // timelapse profiles do not list audio profiles
        if (cp.quality >= QUALITY_TIME_LAPSE_LIST_START
                && cp.quality <= QUALITY_TIME_LAPSE_LIST_END) {
            audioProfiles = new EncoderProfiles.AudioProfile[] { };
        } else {
            audioProfiles = new EncoderProfiles.AudioProfile[] {
                new EncoderProfiles.AudioProfile(
                        cp.audioCodec,
                        cp.audioChannels,
                        cp.audioSampleRate,
                        cp.audioBitRate)
            };
        }

        return new EncoderProfiles(
                cp.duration,
                cp.fileFormat,
                new EncoderProfiles.VideoProfile[] {
                    new EncoderProfiles.VideoProfile(
                        cp.videoCodec,
                        cp.videoFrameWidth,
                        cp.videoFrameHeight,
                        cp.videoFrameRate,
                        cp.videoBitRate,
                        0 /* TODO: get profile */)
                },
                audioProfiles);
    }

    /**
     * Returns true if a camcorder profile exists for the first back-facing
     * camera at the given quality level.
     * camera at the given quality level.
     *
     *
     * <p>
     * <p>
@@ -507,7 +671,7 @@ public class CamcorderProfile
    }
    }


    /**
    /**
     * Returns true if camcorder profile exists for the given camera at
     * Returns true if a camcorder profile exists for the given camera at
     * the given quality level.
     * the given quality level.
     *
     *
     * <p>
     * <p>
+351 −0
Original line number Original line Diff line number Diff line
/*
 * Copyright (C) 2021 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 android.media;

import android.annotation.NonNull;

import java.util.Arrays;
import java.util.Collections;
import java.util.List;

/**
 * Describes a set of encoding profiles for a given media (audio and/or video) profile.
 * These settings are read-only.
 *
 * <p>Currently, this is used to describe camera recording profile with more detail than {@link
 * CamcorderProfile}, by providing encoding parameters for more than just the default audio
 * and/or video codec.
 *
 * <p>The compressed output from a camera recording session contains two tracks:
 * one for audio and one for video.
 * <p>In the future audio-only recording profiles may be defined.
 *
 * <p>Each media profile specifies a set of audio and a set of video specific settings.
 * <ul>
 * <li> The file output format
 * <li> Default file duration
 * <p>Video-specific settings are:
 * <li> Video codec format
 * <li> Video bit rate in bits per second
 * <li> Video frame rate in frames per second
 * <li> Video frame width and height,
 * <li> Video encoder profile.
 * <p>Audio-specific settings are:
 * <li> Audio codec format
 * <li> Audio bit rate in bits per second,
 * <li> Audio sample rate
 * <li> Number of audio channels for recording.
 * </ul>
 */
public class EncoderProfiles
{
    /**
     * Default recording duration in seconds before the session is terminated.
     * This is useful for applications like MMS has limited file size requirement.
     * This could be 0 if there is no default recording duration.
     */
    public int getDurationSeconds() {
        return durationSecs;
    }

    /**
     * Recommended output file format
     * @see android.media.MediaRecorder.OutputFormat
     */
    public int getFileFormat() {
        return fileFormat;
    }

    /**
     * Configuration for a video encoder.
     */
    public static class VideoProfile {
        /**
         * The video encoder being used for the video track
         * @see android.media.MediaRecorder.VideoEncoder
         */
        public int getCodec() {
            return codec;
        }

        /**
         * The media type of the video encoder being used for the video track
         * @see android.media.MediaFormat#KEY_MIME
         */
        public @NonNull String getMediaType() {
            if (codec == MediaRecorder.VideoEncoder.H263) {
                return MediaFormat.MIMETYPE_VIDEO_H263;
            } else if (codec == MediaRecorder.VideoEncoder.H264) {
                return MediaFormat.MIMETYPE_VIDEO_AVC;
            } else if (codec == MediaRecorder.VideoEncoder.MPEG_4_SP) {
                return MediaFormat.MIMETYPE_VIDEO_MPEG4;
            } else if (codec == MediaRecorder.VideoEncoder.VP8) {
                return MediaFormat.MIMETYPE_VIDEO_VP8;
            } else if (codec == MediaRecorder.VideoEncoder.HEVC) {
                return MediaFormat.MIMETYPE_VIDEO_HEVC;
            }
            // we should never be here
            throw new RuntimeException("Unknown codec");
        }

        /**
         * The target video output bitrate in bits per second
         * <p>
         * This is the target recorded video output bitrate if the application configures the video
         * recording via {@link MediaRecorder#setProfile} without specifying any other
         * {@link MediaRecorder} encoding parameters. For example, for high speed quality profiles
         * (from {@link CamcorderProfile#QUALITY_HIGH_SPEED_LOW} to {@link
         * CamcorderProfile#QUALITY_HIGH_SPEED_2160P}), this is the bitrate where the video is
         * recorded with. If the application intends to record slow motion videos with the high
         * speed quality profiles, it must set a different video bitrate that is corresponding to
         * the desired recording output bit rate (i.e., the encoded video bitrate during normal
         * playback) via {@link MediaRecorder#setVideoEncodingBitRate}. For example, if {@link
         * CamcorderProfile#QUALITY_HIGH_SPEED_720P} advertises 240fps {@link #getFrameRate} and
         * 64Mbps {@link #getBitrate} in the high speed VideoProfile, and the application
         * intends to record 1/8 factor slow motion recording videos, the application must set 30fps
         * via {@link MediaRecorder#setVideoFrameRate} and 8Mbps ( {@link #getBitrate} * slow motion
         * factor) via {@link MediaRecorder#setVideoEncodingBitRate}. Failing to do so will result
         * in videos with unexpected frame rate and bit rate, or {@link MediaRecorder} error if the
         * output bit rate exceeds the encoder limit. If the application intends to do the video
         * recording with {@link MediaCodec} encoder, it must set each individual field of {@link
         * MediaFormat} similarly according to this VideoProfile.
         * </p>
         *
         * @see #getFrameRate
         * @see MediaRecorder
         * @see MediaCodec
         * @see MediaFormat
         */
        public int getBitrate() {
            return bitrate;
        }

        /**
         * The target video frame rate in frames per second.
         * <p>
         * This is the target recorded video output frame rate per second if the application
         * configures the video recording via {@link MediaRecorder#setProfile} without specifying
         * any other {@link MediaRecorder} encoding parameters. For example, for high speed quality
         * profiles (from {@link CamcorderProfile#QUALITY_HIGH_SPEED_LOW} to {@link
         * CamcorderProfile#QUALITY_HIGH_SPEED_2160P}), this is the frame rate where the video is
         * recorded and played back with. If the application intends to create slow motion use case
         * with the high speed quality profiles, it must set a different video frame rate that is
         * corresponding to the desired output (playback) frame rate via {@link
         * MediaRecorder#setVideoFrameRate}. For example, if {@link
         * CamcorderProfile#QUALITY_HIGH_SPEED_720P} advertises 240fps {@link #getFrameRate}
         * in the VideoProfile, and the application intends to create 1/8 factor slow motion
         * recording videos, the application must set 30fps via {@link
         * MediaRecorder#setVideoFrameRate}. Failing to do so will result in high speed videos with
         * normal speed playback frame rate (240fps for above example). If the application intends
         * to do the video recording with {@link MediaCodec} encoder, it must set each individual
         * field of {@link MediaFormat} similarly according to this VideoProfile.
         * </p>
         *
         * @see #getBitrate
         * @see MediaRecorder
         * @see MediaCodec
         * @see MediaFormat
         */
        public int getFrameRate() {
            return frameRate;
        }

        /**
         * The target video frame width in pixels
         */
        public int getWidth() {
            return width;
        }

        /**
         * The target video frame height in pixels
         */
        public int getHeight() {
            return height;
        }

        /**
         * The video encoder profile being used for the video track.
         * <p>
         * This value is 0 if there is no profile defined for the video codec.
         *
         * @see MediaRecorder#setVideoEncodingProfileLevel
         * @see MediaFormat#KEY_PROFILE
         */
        public int getProfile() {
            return profile;
        }

        // Constructor called by JNI and CamcorderProfile
        /* package private */ VideoProfile(int codec,
                             int width,
                             int height,
                             int frameRate,
                             int bitrate,
                             int profile) {
            this.codec = codec;
            this.width = width;
            this.height = height;
            this.frameRate = frameRate;
            this.bitrate = bitrate;
            this.profile = profile;
        }

        private int codec;
        private int width;
        private int height;
        private int frameRate;
        private int bitrate;
        private int profile;
    }

    /**
     * Returns the defined audio encoder profiles.
     * <p>
     * The list may be empty. This means there are no audio encoder
     * profiles defined. Otherwise, the first profile is the default
     * audio profile.
     */
    public @NonNull List<AudioProfile> getAudioProfiles() {
        return audioProfiles;
    }

    /**
     * Returns the defined video encoder profiles.
     * <p>
     * The list may be empty. This means there are no video encoder
     * profiles defined. Otherwise, the first profile is the default
     * video profile.
     */
    public @NonNull List<VideoProfile> getVideoProfiles() {
        return videoProfiles;
    }

    /**
     * Configuration for an audio encoder.
     */
    public static class AudioProfile {
        /**
         * The audio encoder being used for the audio track.
         * @see android.media.MediaRecorder.AudioEncoder
         */
        public int getCodec() {
            return codec;
        }

        /**
         * The media type of the audio encoder being used for the video track
         * @see android.media.MediaFormat#KEY_MIME
         */
        public @NonNull String getMediaType() {
            if (codec == MediaRecorder.AudioEncoder.AMR_NB) {
                return MediaFormat.MIMETYPE_AUDIO_AMR_NB;
            } else if (codec == MediaRecorder.AudioEncoder.AMR_WB) {
                return MediaFormat.MIMETYPE_AUDIO_AMR_WB;
            } else if (codec == MediaRecorder.AudioEncoder.AAC
                    || codec == MediaRecorder.AudioEncoder.HE_AAC
                    || codec == MediaRecorder.AudioEncoder.AAC_ELD) {
                return MediaFormat.MIMETYPE_AUDIO_AAC;
            } else if (codec == MediaRecorder.AudioEncoder.VORBIS) {
                return MediaFormat.MIMETYPE_AUDIO_VORBIS;
            } else if (codec == MediaRecorder.AudioEncoder.OPUS) {
                return MediaFormat.MIMETYPE_AUDIO_OPUS;
            }
            // we should never be here
            throw new RuntimeException("Unknown codec");
        }

        /**
         * The target audio output bitrate in bits per second
         */
        public int getBitrate() {
            return bitrate;
        }

        /**
         * The audio sampling rate used for the audio track
         */
        public int getSampleRate() {
            return sampleRate;
        }

        /**
         * The number of audio channels used for the audio track
         */
        public int getChannels() {
            return channels;
        }

        /**
         * The audio encoder profile being used for the audio track
         * <p>
         * This value is 0 if there is no profile defined for the audio codec.
         * @see MediaFormat#KEY_PROFILE
         */
        public int getProfile() {
            if (codec == MediaRecorder.AudioEncoder.AAC) {
                return MediaCodecInfo.CodecProfileLevel.AACObjectMain;
            } else if (codec == MediaRecorder.AudioEncoder.HE_AAC) {
                return MediaCodecInfo.CodecProfileLevel.AACObjectHE;
            } else if (codec == MediaRecorder.AudioEncoder.AAC_ELD) {
                return MediaCodecInfo.CodecProfileLevel.AACObjectELD;
            }
            return 0;
        }


        // Constructor called by JNI and CamcorderProfile
        /* package private */ AudioProfile(
                int codec,
                int channels,
                int sampleRate,
                int bitrate) {
            this.codec = codec;
            this.channels = channels;
            this.sampleRate = sampleRate;
            this.bitrate = bitrate;
        }

        private int codec;
        private int channels;
        private int sampleRate;
        private int bitrate;
    }

    //static {
    //    System.loadLibrary("media_jni");
    //native_init();
    //}

    private int durationSecs;
    private int fileFormat;
    // non-modifiable lists
    private @NonNull List<AudioProfile> audioProfiles;
    private @NonNull List<VideoProfile> videoProfiles;

    // Constructor called by JNI and CamcorderProfile
    /* package private */ EncoderProfiles(
            int duration,
            int fileFormat,
            VideoProfile[] videoProfiles,
            AudioProfile[] audioProfiles) {
        this.durationSecs     = duration;
        this.fileFormat       = fileFormat;
        this.videoProfiles    = Collections.unmodifiableList(Arrays.asList(videoProfiles));
        this.audioProfiles    = Collections.unmodifiableList(Arrays.asList(audioProfiles));
    }
}
+41 −1

File changed.

Preview size limit exceeded, changes collapsed.