Merge "media: Implement getAchievableFrameRatesFor with measured frame rate." into mnc-dev
This commit is contained in:
@@ -16,6 +16,8 @@
|
|||||||
|
|
||||||
package android.media;
|
package android.media;
|
||||||
|
|
||||||
|
import android.annotation.NonNull;
|
||||||
|
import android.annotation.Nullable;
|
||||||
import android.util.Log;
|
import android.util.Log;
|
||||||
import android.util.Pair;
|
import android.util.Pair;
|
||||||
import android.util.Range;
|
import android.util.Range;
|
||||||
@@ -1003,6 +1005,7 @@ public final class MediaCodecInfo {
|
|||||||
private Range<Rational> mAspectRatioRange;
|
private Range<Rational> mAspectRatioRange;
|
||||||
private Range<Rational> mBlockAspectRatioRange;
|
private Range<Rational> mBlockAspectRatioRange;
|
||||||
private Range<Long> mBlocksPerSecondRange;
|
private Range<Long> mBlocksPerSecondRange;
|
||||||
|
private Map<Size, Range<Long>> mMeasuredFrameRates;
|
||||||
private Range<Integer> mFrameRateRange;
|
private Range<Integer> mFrameRateRange;
|
||||||
|
|
||||||
private int mBlockWidth;
|
private int mBlockWidth;
|
||||||
@@ -1195,6 +1198,28 @@ public final class MediaCodecInfo {
|
|||||||
(double) mFrameRateRange.getUpper()));
|
(double) mFrameRateRange.getUpper()));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@NonNull
|
||||||
|
private Size findClosestSize(int width, int height) {
|
||||||
|
int targetPixels = width * height;
|
||||||
|
Size closestSize = null;
|
||||||
|
int mimPixelsDiff = Integer.MAX_VALUE;
|
||||||
|
for (Size size : mMeasuredFrameRates.keySet()) {
|
||||||
|
int pixelsDiff = Math.abs(targetPixels - size.getWidth() * size.getHeight());
|
||||||
|
if (pixelsDiff < mimPixelsDiff) {
|
||||||
|
mimPixelsDiff = pixelsDiff;
|
||||||
|
closestSize = size;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return closestSize;
|
||||||
|
}
|
||||||
|
|
||||||
|
private Range<Double> estimateFrameRatesFor(int width, int height) {
|
||||||
|
Size size = findClosestSize(width, height);
|
||||||
|
Range<Long> range = mMeasuredFrameRates.get(size);
|
||||||
|
Double ratio = (double)(width * height) / (size.getWidth() * size.getHeight());
|
||||||
|
return Range.create(range.getLower() * ratio, range.getUpper() * ratio);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the range of achievable video frame rates for a video size.
|
* Returns the range of achievable video frame rates for a video size.
|
||||||
* May return {@code null}, if the codec did not publish any measurement
|
* May return {@code null}, if the codec did not publish any measurement
|
||||||
@@ -1208,14 +1233,20 @@ public final class MediaCodecInfo {
|
|||||||
*
|
*
|
||||||
* @throws IllegalArgumentException if the video size is not supported.
|
* @throws IllegalArgumentException if the video size is not supported.
|
||||||
*/
|
*/
|
||||||
|
@Nullable
|
||||||
public Range<Double> getAchievableFrameRatesFor(int width, int height) {
|
public Range<Double> getAchievableFrameRatesFor(int width, int height) {
|
||||||
if (!supports(width, height, null)) {
|
if (!supports(width, height, null)) {
|
||||||
throw new IllegalArgumentException("unsupported size");
|
throw new IllegalArgumentException("unsupported size");
|
||||||
}
|
}
|
||||||
// TODO: get this data from the codec
|
|
||||||
|
if (mMeasuredFrameRates == null || mMeasuredFrameRates.size() <= 0) {
|
||||||
|
Log.w(TAG, "Codec did not publish any measurement data.");
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return estimateFrameRatesFor(width, height);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns whether a given video size ({@code width} and
|
* Returns whether a given video size ({@code width} and
|
||||||
* {@code height}) and {@code frameRate} combination is supported.
|
* {@code height}) and {@code frameRate} combination is supported.
|
||||||
@@ -1346,6 +1377,34 @@ public final class MediaCodecInfo {
|
|||||||
mSmallerDimensionUpperLimit = SIZE_RANGE.getUpper();
|
mSmallerDimensionUpperLimit = SIZE_RANGE.getUpper();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private Map<Size, Range<Long>> getMeasuredFrameRates(Map<String, Object> map) {
|
||||||
|
Map<Size, Range<Long>> ret = new HashMap<Size, Range<Long>>();
|
||||||
|
final String prefix = "measured-frame-rate-";
|
||||||
|
Set<String> keys = map.keySet();
|
||||||
|
for (String key : keys) {
|
||||||
|
// looking for: measured-frame-rate-WIDTHxHEIGHT-range
|
||||||
|
if (!key.startsWith(prefix)) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
String subKey = key.substring(prefix.length());
|
||||||
|
String[] temp = key.split("-");
|
||||||
|
if (temp.length != 5) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
String sizeStr = temp[3];
|
||||||
|
Size size = Utils.parseSize(sizeStr, null);
|
||||||
|
if (size == null || size.getWidth() * size.getHeight() <= 0) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
Range<Long> range = Utils.parseLongRange(map.get(key), null);
|
||||||
|
if (range == null || range.getLower() < 0 || range.getUpper() < 0) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
ret.put(size, range);
|
||||||
|
}
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
private void parseFromInfo(MediaFormat info) {
|
private void parseFromInfo(MediaFormat info) {
|
||||||
final Map<String, Object> map = info.getMap();
|
final Map<String, Object> map = info.getMap();
|
||||||
Size blockSize = new Size(mBlockWidth, mBlockHeight);
|
Size blockSize = new Size(mBlockWidth, mBlockHeight);
|
||||||
@@ -1360,6 +1419,7 @@ public final class MediaCodecInfo {
|
|||||||
counts = Utils.parseIntRange(map.get("block-count-range"), null);
|
counts = Utils.parseIntRange(map.get("block-count-range"), null);
|
||||||
blockRates =
|
blockRates =
|
||||||
Utils.parseLongRange(map.get("blocks-per-second-range"), null);
|
Utils.parseLongRange(map.get("blocks-per-second-range"), null);
|
||||||
|
mMeasuredFrameRates = getMeasuredFrameRates(map);
|
||||||
{
|
{
|
||||||
Object o = map.get("size-range");
|
Object o = map.get("size-range");
|
||||||
Pair<Size, Size> sizeRange = Utils.parseSizeRange(o);
|
Pair<Size, Size> sizeRange = Utils.parseSizeRange(o);
|
||||||
|
|||||||
Reference in New Issue
Block a user