Skip to content
Toggle navigation
P
Projects
G
Groups
S
Snippets
Help
SDK
/
exoplayer
This project
Loading...
Sign in
Toggle navigation
Go to a project
Project
Repository
Issues
0
Merge Requests
0
Pipelines
Wiki
Snippets
Settings
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Commit
d1357e8b
authored
Jun 20, 2022
by
huangdarwin
Committed by
Ian Baker
Jun 27, 2022
Browse files
Options
_('Browse Files')
Download
Email Patches
Plain Diff
FrameProcessor: Use factories instead of a builder for Presentation.
PiperOrigin-RevId: 456064021
parent
a444bb8c
Hide whitespace changes
Inline
Side-by-side
Showing
6 changed files
with
109 additions
and
120 deletions
library/transformer/src/androidTest/java/com/google/android/exoplayer2/transformer/FrameProcessorChainPixelTest.java
library/transformer/src/androidTest/java/com/google/android/exoplayer2/transformer/PresentationPixelTest.java
library/transformer/src/main/java/com/google/android/exoplayer2/transformer/FrameProcessorChain.java
library/transformer/src/main/java/com/google/android/exoplayer2/transformer/Presentation.java
library/transformer/src/main/java/com/google/android/exoplayer2/transformer/VideoTranscodingSamplePipeline.java
library/transformer/src/test/java/com/google/android/exoplayer2/transformer/PresentationTest.java
library/transformer/src/androidTest/java/com/google/android/exoplayer2/transformer/FrameProcessorChainPixelTest.java
View file @
d1357e8b
...
...
@@ -204,10 +204,10 @@ public final class FrameProcessorChainPixelTest {
}
@Test
public
void
processData_withPresentation_
setResolution_producesExpectedOutput
()
throws
Exception
{
String
testId
=
"processData_withPresentation_setResolution"
;
setUpAndPrepareFirstFrame
(
DEFAULT_PIXEL_WIDTH_HEIGHT_RATIO
,
new
Presentation
.
Builder
().
setResolution
(
480
).
build
(
));
public
void
processData_withPresentation_
createForHeight_producesExpectedOutput
()
throws
Exception
{
String
testId
=
"processData_withPresentation_createForHeight"
;
setUpAndPrepareFirstFrame
(
DEFAULT_PIXEL_WIDTH_HEIGHT_RATIO
,
Presentation
.
createForHeight
(
480
));
Bitmap
expectedBitmap
=
BitmapTestUtil
.
readBitmap
(
REQUEST_OUTPUT_HEIGHT_PNG_ASSET_PATH
);
Bitmap
actualBitmap
=
processFirstFrameAndEnd
();
...
...
@@ -222,14 +222,13 @@ public final class FrameProcessorChainPixelTest {
}
@Test
public
void
processData_withCrop
And
Presentation_producesExpectedOutput
()
throws
Exception
{
String
testId
=
"processData_withCrop
And
Presentation"
;
public
void
processData_withCrop
Then
Presentation_producesExpectedOutput
()
throws
Exception
{
String
testId
=
"processData_withCrop
Then
Presentation"
;
setUpAndPrepareFirstFrame
(
DEFAULT_PIXEL_WIDTH_HEIGHT_RATIO
,
new
Crop
(
/* left= */
-.
5
f
,
/* right= */
.
5
f
,
/* bottom= */
-.
5
f
,
/* top= */
.
5
f
),
new
Presentation
.
Builder
()
.
setAspectRatio
(
/* aspectRatio= */
.
5
f
,
Presentation
.
LAYOUT_SCALE_TO_FIT
)
.
build
());
Presentation
.
createForAspectRatio
(
/* aspectRatio= */
.
5
f
,
Presentation
.
LAYOUT_SCALE_TO_FIT
));
Bitmap
expectedBitmap
=
BitmapTestUtil
.
readBitmap
(
CROP_THEN_ASPECT_RATIO_PNG_ASSET_PATH
);
Bitmap
actualBitmap
=
processFirstFrameAndEnd
();
...
...
library/transformer/src/androidTest/java/com/google/android/exoplayer2/transformer/PresentationPixelTest.java
View file @
d1357e8b
...
...
@@ -27,6 +27,7 @@ import android.opengl.EGLDisplay;
import
android.opengl.EGLSurface
;
import
android.util.Size
;
import
androidx.test.ext.junit.runners.AndroidJUnit4
;
import
com.google.android.exoplayer2.C
;
import
com.google.android.exoplayer2.util.GlUtil
;
import
java.io.IOException
;
import
org.checkerframework.checker.nullness.qual.MonotonicNonNull
;
...
...
@@ -95,7 +96,8 @@ public final class PresentationPixelTest {
@Test
public
void
drawFrame_noEdits_producesExpectedOutput
()
throws
Exception
{
String
testId
=
"drawFrame_noEdits"
;
presentationTextureProcessor
=
new
Presentation
.
Builder
().
build
().
toGlTextureProcessor
(
context
);
presentationTextureProcessor
=
Presentation
.
createForHeight
(
C
.
LENGTH_UNSET
).
toGlTextureProcessor
(
context
);
Size
outputSize
=
presentationTextureProcessor
.
configure
(
inputWidth
,
inputHeight
);
setupOutputTexture
(
outputSize
.
getWidth
(),
outputSize
.
getHeight
());
Bitmap
expectedBitmap
=
BitmapTestUtil
.
readBitmap
(
ORIGINAL_PNG_ASSET_PATH
);
...
...
@@ -119,9 +121,7 @@ public final class PresentationPixelTest {
throws
Exception
{
String
testId
=
"drawFrame_changeAspectRatio_scaleToFit_narrow"
;
presentationTextureProcessor
=
new
Presentation
.
Builder
()
.
setAspectRatio
(
1
f
,
Presentation
.
LAYOUT_SCALE_TO_FIT
)
.
build
()
Presentation
.
createForAspectRatio
(
/* aspectRatio= */
1
f
,
Presentation
.
LAYOUT_SCALE_TO_FIT
)
.
toGlTextureProcessor
(
context
);
Size
outputSize
=
presentationTextureProcessor
.
configure
(
inputWidth
,
inputHeight
);
setupOutputTexture
(
outputSize
.
getWidth
(),
outputSize
.
getHeight
());
...
...
@@ -147,9 +147,7 @@ public final class PresentationPixelTest {
throws
Exception
{
String
testId
=
"drawFrame_changeAspectRatio_scaleToFit_wide"
;
presentationTextureProcessor
=
new
Presentation
.
Builder
()
.
setAspectRatio
(
2
f
,
Presentation
.
LAYOUT_SCALE_TO_FIT
)
.
build
()
Presentation
.
createForAspectRatio
(
/* aspectRatio= */
2
f
,
Presentation
.
LAYOUT_SCALE_TO_FIT
)
.
toGlTextureProcessor
(
context
);
Size
outputSize
=
presentationTextureProcessor
.
configure
(
inputWidth
,
inputHeight
);
setupOutputTexture
(
outputSize
.
getWidth
(),
outputSize
.
getHeight
());
...
...
@@ -175,9 +173,8 @@ public final class PresentationPixelTest {
throws
Exception
{
String
testId
=
"drawFrame_changeAspectRatio_scaleToFitWithCrop_narrow"
;
presentationTextureProcessor
=
new
Presentation
.
Builder
()
.
setAspectRatio
(
1
f
,
Presentation
.
LAYOUT_SCALE_TO_FIT_WITH_CROP
)
.
build
()
Presentation
.
createForAspectRatio
(
/* aspectRatio= */
1
f
,
Presentation
.
LAYOUT_SCALE_TO_FIT_WITH_CROP
)
.
toGlTextureProcessor
(
context
);
Size
outputSize
=
presentationTextureProcessor
.
configure
(
inputWidth
,
inputHeight
);
setupOutputTexture
(
outputSize
.
getWidth
(),
outputSize
.
getHeight
());
...
...
@@ -203,9 +200,8 @@ public final class PresentationPixelTest {
throws
Exception
{
String
testId
=
"drawFrame_changeAspectRatio_scaleToFitWithCrop_wide"
;
presentationTextureProcessor
=
new
Presentation
.
Builder
()
.
setAspectRatio
(
2
f
,
Presentation
.
LAYOUT_SCALE_TO_FIT_WITH_CROP
)
.
build
()
Presentation
.
createForAspectRatio
(
/* aspectRatio= */
2
f
,
Presentation
.
LAYOUT_SCALE_TO_FIT_WITH_CROP
)
.
toGlTextureProcessor
(
context
);
Size
outputSize
=
presentationTextureProcessor
.
configure
(
inputWidth
,
inputHeight
);
setupOutputTexture
(
outputSize
.
getWidth
(),
outputSize
.
getHeight
());
...
...
@@ -231,9 +227,7 @@ public final class PresentationPixelTest {
throws
Exception
{
String
testId
=
"drawFrame_changeAspectRatio_stretchToFit_narrow"
;
presentationTextureProcessor
=
new
Presentation
.
Builder
()
.
setAspectRatio
(
1
f
,
Presentation
.
LAYOUT_STRETCH_TO_FIT
)
.
build
()
Presentation
.
createForAspectRatio
(
/* aspectRatio= */
1
f
,
Presentation
.
LAYOUT_STRETCH_TO_FIT
)
.
toGlTextureProcessor
(
context
);
Size
outputSize
=
presentationTextureProcessor
.
configure
(
inputWidth
,
inputHeight
);
setupOutputTexture
(
outputSize
.
getWidth
(),
outputSize
.
getHeight
());
...
...
@@ -259,9 +253,7 @@ public final class PresentationPixelTest {
throws
Exception
{
String
testId
=
"drawFrame_changeAspectRatio_stretchToFit_wide"
;
presentationTextureProcessor
=
new
Presentation
.
Builder
()
.
setAspectRatio
(
2
f
,
Presentation
.
LAYOUT_STRETCH_TO_FIT
)
.
build
()
Presentation
.
createForAspectRatio
(
/* aspectRatio= */
2
f
,
Presentation
.
LAYOUT_STRETCH_TO_FIT
)
.
toGlTextureProcessor
(
context
);
Size
outputSize
=
presentationTextureProcessor
.
configure
(
inputWidth
,
inputHeight
);
setupOutputTexture
(
outputSize
.
getWidth
(),
outputSize
.
getHeight
());
...
...
library/transformer/src/main/java/com/google/android/exoplayer2/transformer/FrameProcessorChain.java
View file @
d1357e8b
...
...
@@ -259,12 +259,8 @@ import org.checkerframework.checker.nullness.qual.MonotonicNonNull;
if
(
outputSurfaceInfo
.
width
!=
outputSize
.
getWidth
()
||
outputSurfaceInfo
.
height
!=
outputSize
.
getHeight
())
{
matrixTransformationListBuilder
.
add
(
new
Presentation
.
Builder
()
.
setAspectRatio
(
outputSurfaceInfo
.
width
/
(
float
)
outputSurfaceInfo
.
height
,
Presentation
.
LAYOUT_SCALE_TO_FIT
)
.
setResolution
(
outputSurfaceInfo
.
height
)
.
build
());
Presentation
.
createForWidthAndHeight
(
outputSurfaceInfo
.
width
,
outputSurfaceInfo
.
height
,
Presentation
.
LAYOUT_SCALE_TO_FIT
));
}
// Convert final list of matrix transformations (including additional transformations for the
...
...
library/transformer/src/main/java/com/google/android/exoplayer2/transformer/Presentation.java
View file @
d1357e8b
...
...
@@ -35,8 +35,6 @@ import org.checkerframework.checker.nullness.qual.RequiresNonNull;
* the input pixels onto the output frame geometry (for example, by stretching the input frame to
* match the specified output frame, or fitting the input frame using letterboxing).
*
* <p>Aspect ratio is applied before setting resolution.
*
* <p>The background color of the output frame will be black, with alpha = 0 if applicable.
*/
public
final
class
Presentation
implements
MatrixTransformation
{
...
...
@@ -47,8 +45,7 @@ public final class Presentation implements MatrixTransformation {
* <p>One of {@link #LAYOUT_SCALE_TO_FIT}, {@link #LAYOUT_SCALE_TO_FIT_WITH_CROP}, or {@link
* #LAYOUT_STRETCH_TO_FIT}.
*
* <p>May scale either width or height, leaving the other output dimension equal to its input,
* unless {@link Builder#setResolution(int)} rescales width and height.
* <p>May scale either width or height, leaving the other output dimension equal to its input.
*/
@Documented
@Retention
(
SOURCE
)
...
...
@@ -98,81 +95,82 @@ public final class Presentation implements MatrixTransformation {
*/
public
static
final
int
LAYOUT_STRETCH_TO_FIT
=
2
;
/** A builder for {@link Presentation} instances. */
public
static
final
class
Builder
{
// Optional fields.
private
int
outputHeight
;
private
float
aspectRatio
;
private
@Layout
int
layout
;
private
static
final
float
ASPECT_RATIO_UNSET
=
-
1
f
;
/** Creates a builder with default values. */
public
Builder
()
{
outputHeight
=
C
.
LENGTH_UNSET
;
aspectRatio
=
C
.
LENGTH_UNSET
;
}
private
static
void
checkLayout
(
@Layout
int
layout
)
{
checkArgument
(
layout
==
LAYOUT_SCALE_TO_FIT
||
layout
==
LAYOUT_SCALE_TO_FIT_WITH_CROP
||
layout
==
LAYOUT_STRETCH_TO_FIT
,
"invalid layout "
+
layout
);
}
/**
* Sets the output resolution using the output height
.
*
* <p>The default value, {@link C#LENGTH_UNSET}, corresponds to using the same height as the
* input. Output width of the displayed frame will scale to preserve the frame's aspect ratio
* after other transformations.
*
* <p>For example, a 1920x1440 frame can be scaled to 640x480 by calling {@code
* setResolution(480)}.
*
* @param height The output height of the displayed frame, in pixels.
* @return This builder.
*/
public
Builder
setResolution
(
int
height
)
{
this
.
outputHeight
=
height
;
return
this
;
}
/**
* Creates a new {@link Presentation} instance
.
*
* <p>The output frame will have the given aspect ratio (width/height ratio). Width or height will
* be resized to conform to this {@code aspectRatio}, given a {@link Layout}.
*
* @param aspectRatio The aspect ratio (width/height ratio) of the output frame. Must be positive.
* @param layout The layout of the output frame.
*/
public
static
Presentation
createForAspectRatio
(
float
aspectRatio
,
@Layout
int
layout
)
{
checkArgument
(
aspectRatio
==
C
.
LENGTH_UNSET
||
aspectRatio
>
0
,
"aspect ratio "
+
aspectRatio
+
" must be positive or unset"
);
checkLayout
(
layout
);
return
new
Presentation
(
/* width= */
C
.
LENGTH_UNSET
,
/* height= */
C
.
LENGTH_UNSET
,
aspectRatio
,
layout
)
;
}
/**
* Sets the aspect ratio (width/height ratio) for the output frame.
*
* <p>Resizes a frame's width or height to conform to an {@code aspectRatio}, given a {@link
* Layout}. {@code aspectRatio} defaults to {@link C#LENGTH_UNSET}, which corresponds to the
* same aspect ratio as the input frame. {@code layout} defaults to {@link #LAYOUT_SCALE_TO_FIT}
*
* <p>Width and height values set may be rescaled by {@link #setResolution(int)}, which is
* applied after aspect ratio changes.
*
* @param aspectRatio The aspect ratio (width/height ratio) of the output frame. Must be
* positive.
* @return This builder.
*/
public
Builder
setAspectRatio
(
float
aspectRatio
,
@Layout
int
layout
)
{
checkArgument
(
aspectRatio
>
0
,
"aspect ratio "
+
aspectRatio
+
" must be positive"
);
checkArgument
(
layout
==
LAYOUT_SCALE_TO_FIT
||
layout
==
LAYOUT_SCALE_TO_FIT_WITH_CROP
||
layout
==
LAYOUT_STRETCH_TO_FIT
,
"invalid layout "
+
layout
);
this
.
aspectRatio
=
aspectRatio
;
this
.
layout
=
layout
;
return
this
;
}
/**
* Creates a new {@link Presentation} instance.
*
* <p>The output frame will have the given height. Width will scale to preserve the input aspect
* ratio.
*
* @param height The height of the output frame, in pixels.
*/
public
static
Presentation
createForHeight
(
int
height
)
{
return
new
Presentation
(
/* width= */
C
.
LENGTH_UNSET
,
height
,
ASPECT_RATIO_UNSET
,
LAYOUT_SCALE_TO_FIT
);
}
public
Presentation
build
()
{
return
new
Presentation
(
outputHeight
,
aspectRatio
,
layout
);
}
/**
* Creates a new {@link Presentation} instance.
*
* <p>The output frame will have the given width and height, given a {@link Layout}.
*
* <p>Width and height must be positive integers representing the output frame's width and height.
*
* @param width The width of the output frame, in pixels.
* @param height The height of the output frame, in pixels.
* @param layout The layout of the output frame.
*/
public
static
Presentation
createForWidthAndHeight
(
int
width
,
int
height
,
@Layout
int
layout
)
{
checkArgument
(
width
>
0
,
"width "
+
width
+
" must be positive"
);
checkArgument
(
height
>
0
,
"height "
+
height
+
" must be positive"
);
checkLayout
(
layout
);
return
new
Presentation
(
width
,
height
,
ASPECT_RATIO_UNSET
,
layout
);
}
private
final
int
requestedWidthPixels
;
private
final
int
requestedHeightPixels
;
private
f
inal
f
loat
requestedAspectRatio
;
private
float
requestedAspectRatio
;
private
final
@Layout
int
layout
;
private
float
outputWidth
;
private
float
outputHeight
;
private
@MonotonicNonNull
Matrix
transformationMatrix
;
/** Creates a new instance. */
private
Presentation
(
int
requestedHeightPixels
,
float
requestedAspectRatio
,
@Layout
int
layout
)
{
this
.
requestedHeightPixels
=
requestedHeightPixels
;
this
.
requestedAspectRatio
=
requestedAspectRatio
;
private
Presentation
(
int
width
,
int
height
,
float
aspectRatio
,
@Layout
int
layout
)
{
checkArgument
(
(
aspectRatio
==
C
.
LENGTH_UNSET
)
||
(
width
==
C
.
LENGTH_UNSET
),
"width and aspect ratio should not both be set"
);
this
.
requestedWidthPixels
=
width
;
this
.
requestedHeightPixels
=
height
;
this
.
requestedAspectRatio
=
aspectRatio
;
this
.
layout
=
layout
;
outputWidth
=
C
.
LENGTH_UNSET
;
...
...
@@ -189,13 +187,21 @@ public final class Presentation implements MatrixTransformation {
outputWidth
=
inputWidth
;
outputHeight
=
inputHeight
;
if
((
requestedWidthPixels
!=
C
.
LENGTH_UNSET
)
&&
(
requestedHeightPixels
!=
C
.
LENGTH_UNSET
))
{
requestedAspectRatio
=
(
float
)
requestedWidthPixels
/
requestedHeightPixels
;
}
if
(
requestedAspectRatio
!=
C
.
LENGTH_UNSET
)
{
applyAspectRatio
();
}
// Scale width and height to desired requestedHeightPixels, preserving aspect ratio.
if
(
requestedHeightPixels
!=
C
.
LENGTH_UNSET
&&
requestedHeightPixels
!=
outputHeight
)
{
outputWidth
=
requestedHeightPixels
*
outputWidth
/
outputHeight
;
// Scale output width and height to requested values.
if
(
requestedHeightPixels
!=
C
.
LENGTH_UNSET
)
{
if
(
requestedWidthPixels
!=
C
.
LENGTH_UNSET
)
{
outputWidth
=
requestedWidthPixels
;
}
else
{
outputWidth
=
requestedHeightPixels
*
outputWidth
/
outputHeight
;
}
outputHeight
=
requestedHeightPixels
;
}
return
new
Size
(
Math
.
round
(
outputWidth
),
Math
.
round
(
outputHeight
));
...
...
library/transformer/src/main/java/com/google/android/exoplayer2/transformer/VideoTranscodingSamplePipeline.java
View file @
d1357e8b
...
...
@@ -88,8 +88,7 @@ import org.checkerframework.dataflow.qual.Pure;
.
build
());
}
if
(
transformationRequest
.
outputHeight
!=
C
.
LENGTH_UNSET
)
{
effectsListBuilder
.
add
(
new
Presentation
.
Builder
().
setResolution
(
transformationRequest
.
outputHeight
).
build
());
effectsListBuilder
.
add
(
Presentation
.
createForHeight
(
transformationRequest
.
outputHeight
));
}
AtomicReference
<
TransformationException
>
encoderInitializationException
=
...
...
library/transformer/src/test/java/com/google/android/exoplayer2/transformer/PresentationTest.java
View file @
d1357e8b
...
...
@@ -19,6 +19,7 @@ import static com.google.common.truth.Truth.assertThat;
import
android.util.Size
;
import
androidx.test.ext.junit.runners.AndroidJUnit4
;
import
com.google.android.exoplayer2.C
;
import
org.junit.Test
;
import
org.junit.runner.RunWith
;
...
...
@@ -33,7 +34,7 @@ public final class PresentationTest {
public
void
configure_noEdits_leavesFramesUnchanged
()
{
int
inputWidth
=
200
;
int
inputHeight
=
150
;
Presentation
presentation
=
new
Presentation
.
Builder
().
build
(
);
Presentation
presentation
=
Presentation
.
createForHeight
(
C
.
LENGTH_UNSET
);
Size
outputSize
=
presentation
.
configure
(
inputWidth
,
inputHeight
);
...
...
@@ -42,11 +43,11 @@ public final class PresentationTest {
}
@Test
public
void
configure_
setResolution
_changesDimensions
()
{
public
void
configure_
createForHeight
_changesDimensions
()
{
int
inputWidth
=
200
;
int
inputHeight
=
150
;
int
requestedHeight
=
300
;
Presentation
presentation
=
new
Presentation
.
Builder
().
setResolution
(
requestedHeight
).
build
(
);
Presentation
presentation
=
Presentation
.
createForHeight
(
requestedHeight
);
Size
outputSize
=
presentation
.
configure
(
inputWidth
,
inputHeight
);
...
...
@@ -55,14 +56,12 @@ public final class PresentationTest {
}
@Test
public
void
configure_
set
AspectRatio_changesDimensions
()
{
public
void
configure_
createFor
AspectRatio_changesDimensions
()
{
int
inputWidth
=
300
;
int
inputHeight
=
200
;
float
aspectRatio
=
2
f
;
Presentation
presentation
=
new
Presentation
.
Builder
()
.
setAspectRatio
(
aspectRatio
,
Presentation
.
LAYOUT_SCALE_TO_FIT
)
.
build
();
Presentation
.
createForAspectRatio
(
aspectRatio
,
Presentation
.
LAYOUT_SCALE_TO_FIT
);
Size
outputSize
=
presentation
.
configure
(
inputWidth
,
inputHeight
);
...
...
@@ -71,20 +70,18 @@ public final class PresentationTest {
}
@Test
public
void
configure_
setAspectRatioAndResolution
_changesDimensions
()
{
public
void
configure_
createForWidthAndHeight
_changesDimensions
()
{
int
inputWidth
=
300
;
int
inputHeight
=
200
;
float
aspectRatio
=
2
f
;
int
requestedHeight
=
1
00
;
int
requestedWidth
=
100
;
int
requestedHeight
=
3
00
;
Presentation
presentation
=
new
Presentation
.
Builder
()
.
setAspectRatio
(
aspectRatio
,
Presentation
.
LAYOUT_SCALE_TO_FIT
)
.
setResolution
(
requestedHeight
)
.
build
();
Presentation
.
createForWidthAndHeight
(
requestedWidth
,
requestedHeight
,
Presentation
.
LAYOUT_SCALE_TO_FIT
);
Size
outputSize
=
presentation
.
configure
(
inputWidth
,
inputHeight
);
assertThat
(
outputSize
.
getWidth
()).
isEqualTo
(
Math
.
round
(
aspectRatio
*
requestedHeight
)
);
assertThat
(
outputSize
.
getWidth
()).
isEqualTo
(
requestedWidth
);
assertThat
(
outputSize
.
getHeight
()).
isEqualTo
(
requestedHeight
);
}
}
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment