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
2416d998
authored
Nov 04, 2020
by
tonihei
Committed by
Andrew Lewis
Nov 06, 2020
Browse files
Options
_('Browse Files')
Download
Email Patches
Plain Diff
Limit target buffer to media configured min/max values.
Issue: #4904 PiperOrigin-RevId: 340653126
parent
c9e80a20
Hide whitespace changes
Inline
Side-by-side
Showing
2 changed files
with
161 additions
and
34 deletions
library/core/src/main/java/com/google/android/exoplayer2/DefaultLivePlaybackSpeedControl.java
library/core/src/test/java/com/google/android/exoplayer2/DefaultLivePlaybackSpeedControlTest.java
library/core/src/main/java/com/google/android/exoplayer2/DefaultLivePlaybackSpeedControl.java
View file @
2416d998
...
...
@@ -122,7 +122,7 @@ public final class DefaultLivePlaybackSpeedControl implements LivePlaybackSpeedC
* @return This builder, for convenience.
*/
public
Builder
setMinUpdateIntervalMs
(
long
minUpdateIntervalMs
)
{
Assertions
.
checkArgument
(
minUpdateIntervalMs
>
=
0
);
Assertions
.
checkArgument
(
minUpdateIntervalMs
>
0
);
this
.
minUpdateIntervalMs
=
minUpdateIntervalMs
;
return
this
;
}
...
...
@@ -160,8 +160,14 @@ public final class DefaultLivePlaybackSpeedControl implements LivePlaybackSpeedC
private
final
long
minUpdateIntervalMs
;
private
final
float
proportionalControlFactor
;
private
LiveConfiguration
mediaConfiguration
;
private
long
mediaConfigurationTargetLiveOffsetUs
;
private
long
targetLiveOffsetOverrideUs
;
private
long
minTargetLiveOffsetUs
;
private
long
maxTargetLiveOffsetUs
;
private
long
currentTargetLiveOffsetUs
;
private
float
maxPlaybackSpeed
;
private
float
minPlaybackSpeed
;
private
float
adjustedPlaybackSpeed
;
private
long
lastPlaybackSpeedUpdateMs
;
...
...
@@ -174,28 +180,42 @@ public final class DefaultLivePlaybackSpeedControl implements LivePlaybackSpeedC
this
.
fallbackMaxPlaybackSpeed
=
fallbackMaxPlaybackSpeed
;
this
.
minUpdateIntervalMs
=
minUpdateIntervalMs
;
this
.
proportionalControlFactor
=
proportionalControlFactor
;
mediaConfiguration
=
LiveConfiguration
.
UNSET
;
mediaConfiguration
TargetLiveOffsetUs
=
C
.
TIME_
UNSET
;
targetLiveOffsetOverrideUs
=
C
.
TIME_UNSET
;
minTargetLiveOffsetUs
=
C
.
TIME_UNSET
;
maxTargetLiveOffsetUs
=
C
.
TIME_UNSET
;
minPlaybackSpeed
=
fallbackMinPlaybackSpeed
;
maxPlaybackSpeed
=
fallbackMaxPlaybackSpeed
;
adjustedPlaybackSpeed
=
1.0f
;
lastPlaybackSpeedUpdateMs
=
C
.
TIME_UNSET
;
currentTargetLiveOffsetUs
=
C
.
TIME_UNSET
;
}
@Override
public
void
setLiveConfiguration
(
LiveConfiguration
liveConfiguration
)
{
this
.
mediaConfiguration
=
liveConfiguration
;
lastPlaybackSpeedUpdateMs
=
C
.
TIME_UNSET
;
mediaConfigurationTargetLiveOffsetUs
=
C
.
msToUs
(
liveConfiguration
.
targetLiveOffsetMs
);
minTargetLiveOffsetUs
=
C
.
msToUs
(
liveConfiguration
.
minLiveOffsetMs
);
maxTargetLiveOffsetUs
=
C
.
msToUs
(
liveConfiguration
.
maxLiveOffsetMs
);
minPlaybackSpeed
=
liveConfiguration
.
minPlaybackSpeed
!=
C
.
RATE_UNSET
?
liveConfiguration
.
minPlaybackSpeed
:
fallbackMinPlaybackSpeed
;
maxPlaybackSpeed
=
liveConfiguration
.
maxPlaybackSpeed
!=
C
.
RATE_UNSET
?
liveConfiguration
.
maxPlaybackSpeed
:
fallbackMaxPlaybackSpeed
;
maybeResetTargetLiveOffsetUs
();
}
@Override
public
void
setTargetLiveOffsetOverrideUs
(
long
liveOffsetUs
)
{
t
his
.
t
argetLiveOffsetOverrideUs
=
liveOffsetUs
;
lastPlaybackSpeedUpdateMs
=
C
.
TIME_UNSET
;
targetLiveOffsetOverrideUs
=
liveOffsetUs
;
maybeResetTargetLiveOffsetUs
()
;
}
@Override
public
float
getAdjustedPlaybackSpeed
(
long
liveOffsetUs
)
{
long
targetLiveOffsetUs
=
getTargetLiveOffsetUs
();
if
(
targetLiveOffsetUs
==
C
.
TIME_UNSET
)
{
if
(
mediaConfigurationTargetLiveOffsetUs
==
C
.
TIME_UNSET
)
{
return
1
f
;
}
if
(
lastPlaybackSpeedUpdateMs
!=
C
.
TIME_UNSET
...
...
@@ -204,34 +224,40 @@ public final class DefaultLivePlaybackSpeedControl implements LivePlaybackSpeedC
}
lastPlaybackSpeedUpdateMs
=
SystemClock
.
elapsedRealtime
();
long
liveOffsetErrorUs
=
liveOffsetUs
-
t
argetLiveOffsetUs
;
long
liveOffsetErrorUs
=
liveOffsetUs
-
currentT
argetLiveOffsetUs
;
if
(
Math
.
abs
(
liveOffsetErrorUs
)
<
MAXIMUM_LIVE_OFFSET_ERROR_US_FOR_UNIT_SPEED
)
{
adjustedPlaybackSpeed
=
1
f
;
}
else
{
float
calculatedSpeed
=
1
f
+
proportionalControlFactor
*
liveOffsetErrorUs
;
adjustedPlaybackSpeed
=
Util
.
constrainValue
(
calculatedSpeed
,
getMinPlaybackSpeed
(),
getMaxPlaybackSpeed
()
);
Util
.
constrainValue
(
calculatedSpeed
,
minPlaybackSpeed
,
maxPlaybackSpeed
);
}
return
adjustedPlaybackSpeed
;
}
@Override
public
long
getTargetLiveOffsetUs
()
{
return
targetLiveOffsetOverrideUs
!=
C
.
TIME_UNSET
&&
mediaConfiguration
.
targetLiveOffsetMs
!=
C
.
TIME_UNSET
?
targetLiveOffsetOverrideUs
:
C
.
msToUs
(
mediaConfiguration
.
targetLiveOffsetMs
);
}
private
float
getMinPlaybackSpeed
()
{
return
mediaConfiguration
.
minPlaybackSpeed
!=
C
.
RATE_UNSET
?
mediaConfiguration
.
minPlaybackSpeed
:
fallbackMinPlaybackSpeed
;
return
currentTargetLiveOffsetUs
;
}
private
float
getMaxPlaybackSpeed
()
{
return
mediaConfiguration
.
maxPlaybackSpeed
!=
C
.
RATE_UNSET
?
mediaConfiguration
.
maxPlaybackSpeed
:
fallbackMaxPlaybackSpeed
;
private
void
maybeResetTargetLiveOffsetUs
()
{
long
idealOffsetUs
=
C
.
TIME_UNSET
;
if
(
mediaConfigurationTargetLiveOffsetUs
!=
C
.
TIME_UNSET
)
{
idealOffsetUs
=
targetLiveOffsetOverrideUs
!=
C
.
TIME_UNSET
?
targetLiveOffsetOverrideUs
:
mediaConfigurationTargetLiveOffsetUs
;
if
(
minTargetLiveOffsetUs
!=
C
.
TIME_UNSET
&&
idealOffsetUs
<
minTargetLiveOffsetUs
)
{
idealOffsetUs
=
minTargetLiveOffsetUs
;
}
if
(
maxTargetLiveOffsetUs
!=
C
.
TIME_UNSET
&&
idealOffsetUs
>
maxTargetLiveOffsetUs
)
{
idealOffsetUs
=
maxTargetLiveOffsetUs
;
}
}
if
(
currentTargetLiveOffsetUs
==
idealOffsetUs
)
{
return
;
}
currentTargetLiveOffsetUs
=
idealOffsetUs
;
lastPlaybackSpeedUpdateMs
=
C
.
TIME_UNSET
;
}
}
library/core/src/test/java/com/google/android/exoplayer2/DefaultLivePlaybackSpeedControlTest.java
View file @
2416d998
...
...
@@ -37,13 +37,13 @@ public class DefaultLivePlaybackSpeedControlTest {
}
@Test
public
void
getTargetLiveOffsetUs_after
Update
LiveConfiguration_usesMediaLiveOffset
()
{
public
void
getTargetLiveOffsetUs_after
Set
LiveConfiguration_usesMediaLiveOffset
()
{
DefaultLivePlaybackSpeedControl
defaultLivePlaybackSpeedControl
=
new
DefaultLivePlaybackSpeedControl
.
Builder
().
build
();
defaultLivePlaybackSpeedControl
.
setLiveConfiguration
(
new
LiveConfiguration
(
/* targetLiveOffsetMs= */
42
,
/* minLiveOffsetMs= */
200
,
/* minLiveOffsetMs= */
5
,
/* maxLiveOffsetMs= */
400
,
/* minPlaybackSpeed= */
1
f
,
/* maxPlaybackSpeed= */
1
f
));
...
...
@@ -52,7 +52,59 @@ public class DefaultLivePlaybackSpeedControlTest {
}
@Test
public
void
getTargetLiveOffsetUs_withOverrideTargetLiveOffsetUs_usesOverride
()
{
public
void
getTargetLiveOffsetUs_afterSetLiveConfigurationWithTargetGreaterThanMax_usesMaxLiveOffset
()
{
DefaultLivePlaybackSpeedControl
defaultLivePlaybackSpeedControl
=
new
DefaultLivePlaybackSpeedControl
.
Builder
().
build
();
defaultLivePlaybackSpeedControl
.
setLiveConfiguration
(
new
LiveConfiguration
(
/* targetLiveOffsetMs= */
4321
,
/* minLiveOffsetMs= */
5
,
/* maxLiveOffsetMs= */
400
,
/* minPlaybackSpeed= */
1
f
,
/* maxPlaybackSpeed= */
1
f
));
assertThat
(
defaultLivePlaybackSpeedControl
.
getTargetLiveOffsetUs
()).
isEqualTo
(
400_000
);
}
@Test
public
void
getTargetLiveOffsetUs_afterSetLiveConfigurationWithTargetLessThanMin_usesMinLiveOffset
()
{
DefaultLivePlaybackSpeedControl
defaultLivePlaybackSpeedControl
=
new
DefaultLivePlaybackSpeedControl
.
Builder
().
build
();
defaultLivePlaybackSpeedControl
.
setLiveConfiguration
(
new
LiveConfiguration
(
/* targetLiveOffsetMs= */
3
,
/* minLiveOffsetMs= */
5
,
/* maxLiveOffsetMs= */
400
,
/* minPlaybackSpeed= */
1
f
,
/* maxPlaybackSpeed= */
1
f
));
assertThat
(
defaultLivePlaybackSpeedControl
.
getTargetLiveOffsetUs
()).
isEqualTo
(
5_000
);
}
@Test
public
void
getTargetLiveOffsetUs_withSetTargetLiveOffsetOverrideUs_usesOverride
()
{
DefaultLivePlaybackSpeedControl
defaultLivePlaybackSpeedControl
=
new
DefaultLivePlaybackSpeedControl
.
Builder
().
build
();
defaultLivePlaybackSpeedControl
.
setTargetLiveOffsetOverrideUs
(
321_000
);
defaultLivePlaybackSpeedControl
.
setLiveConfiguration
(
new
LiveConfiguration
(
/* targetLiveOffsetMs= */
42
,
/* minLiveOffsetMs= */
5
,
/* maxLiveOffsetMs= */
400
,
/* minPlaybackSpeed= */
1
f
,
/* maxPlaybackSpeed= */
1
f
));
long
targetLiveOffsetUs
=
defaultLivePlaybackSpeedControl
.
getTargetLiveOffsetUs
();
assertThat
(
targetLiveOffsetUs
).
isEqualTo
(
321_000
);
}
@Test
public
void
getTargetLiveOffsetUs_withSetTargetLiveOffsetOverrideUsGreaterThanMax_usesMaxLiveOffset
()
{
DefaultLivePlaybackSpeedControl
defaultLivePlaybackSpeedControl
=
new
DefaultLivePlaybackSpeedControl
.
Builder
().
build
();
...
...
@@ -60,19 +112,39 @@ public class DefaultLivePlaybackSpeedControlTest {
defaultLivePlaybackSpeedControl
.
setLiveConfiguration
(
new
LiveConfiguration
(
/* targetLiveOffsetMs= */
42
,
/* minLiveOffsetMs= */
200
,
/* minLiveOffsetMs= */
5
,
/* maxLiveOffsetMs= */
400
,
/* minPlaybackSpeed= */
1
f
,
/* maxPlaybackSpeed= */
1
f
));
long
targetLiveOffsetUs
=
defaultLivePlaybackSpeedControl
.
getTargetLiveOffsetUs
();
assertThat
(
targetLiveOffsetUs
).
isEqualTo
(
123_456_789
);
assertThat
(
targetLiveOffsetUs
).
isEqualTo
(
400_000
);
}
@Test
public
void
getTargetLiveOffsetUs_afterOverrideTargetLiveOffset_withoutMediaConfiguration_returnsUnset
()
{
getTargetLiveOffsetUs_withSetTargetLiveOffsetOverrideUsLessThanMin_usesMinLiveOffset
()
{
DefaultLivePlaybackSpeedControl
defaultLivePlaybackSpeedControl
=
new
DefaultLivePlaybackSpeedControl
.
Builder
().
build
();
defaultLivePlaybackSpeedControl
.
setTargetLiveOffsetOverrideUs
(
3_141
);
defaultLivePlaybackSpeedControl
.
setLiveConfiguration
(
new
LiveConfiguration
(
/* targetLiveOffsetMs= */
42
,
/* minLiveOffsetMs= */
5
,
/* maxLiveOffsetMs= */
400
,
/* minPlaybackSpeed= */
1
f
,
/* maxPlaybackSpeed= */
1
f
));
long
targetLiveOffsetUs
=
defaultLivePlaybackSpeedControl
.
getTargetLiveOffsetUs
();
assertThat
(
targetLiveOffsetUs
).
isEqualTo
(
5_000
);
}
@Test
public
void
getTargetLiveOffsetUs_afterSetTargetLiveOffsetOverrideWithoutMediaConfiguration_returnsUnset
()
{
DefaultLivePlaybackSpeedControl
defaultLivePlaybackSpeedControl
=
new
DefaultLivePlaybackSpeedControl
.
Builder
().
build
();
defaultLivePlaybackSpeedControl
.
setTargetLiveOffsetOverrideUs
(
123_456_789
);
...
...
@@ -84,14 +156,14 @@ public class DefaultLivePlaybackSpeedControlTest {
@Test
public
void
getTargetLiveOffsetUs_after
OverrideTargetLiveOffsetUs
WithTimeUnset_usesMediaLiveOffset
()
{
getTargetLiveOffsetUs_after
SetTargetLiveOffsetOverride
WithTimeUnset_usesMediaLiveOffset
()
{
DefaultLivePlaybackSpeedControl
defaultLivePlaybackSpeedControl
=
new
DefaultLivePlaybackSpeedControl
.
Builder
().
build
();
defaultLivePlaybackSpeedControl
.
setTargetLiveOffsetOverrideUs
(
123_456_789
);
defaultLivePlaybackSpeedControl
.
setLiveConfiguration
(
new
LiveConfiguration
(
/* targetLiveOffsetMs= */
42
,
/* minLiveOffsetMs= */
200
,
/* minLiveOffsetMs= */
5
,
/* maxLiveOffsetMs= */
400
,
/* minPlaybackSpeed= */
1
f
,
/* maxPlaybackSpeed= */
1
f
));
...
...
@@ -294,7 +366,8 @@ public class DefaultLivePlaybackSpeedControlTest {
}
@Test
public
void
adjustPlaybackSpeed_repeatedCallAfterUpdateLiveConfiguration_updatesSpeedAgain
()
{
public
void
adjustPlaybackSpeed_repeatedCallAfterUpdateLiveConfigurationWithSameOffset_returnsSameAdjustedSpeed
()
{
DefaultLivePlaybackSpeedControl
defaultLivePlaybackSpeedControl
=
new
DefaultLivePlaybackSpeedControl
.
Builder
().
setMinUpdateIntervalMs
(
123
).
build
();
defaultLivePlaybackSpeedControl
.
setLiveConfiguration
(
...
...
@@ -317,6 +390,34 @@ public class DefaultLivePlaybackSpeedControlTest {
float
adjustedSpeed2
=
defaultLivePlaybackSpeedControl
.
getAdjustedPlaybackSpeed
(
/* liveOffsetUs= */
2_500_000
);
assertThat
(
adjustedSpeed1
).
isEqualTo
(
adjustedSpeed2
);
}
@Test
public
void
adjustPlaybackSpeed_repeatedCallAfterUpdateLiveConfigurationWithNewOffset_updatesSpeedAgain
()
{
DefaultLivePlaybackSpeedControl
defaultLivePlaybackSpeedControl
=
new
DefaultLivePlaybackSpeedControl
.
Builder
().
setMinUpdateIntervalMs
(
123
).
build
();
defaultLivePlaybackSpeedControl
.
setLiveConfiguration
(
new
LiveConfiguration
(
/* targetLiveOffsetMs= */
2_000
,
/* minLiveOffsetMs= */
C
.
TIME_UNSET
,
/* maxLiveOffsetMs= */
C
.
TIME_UNSET
,
/* minPlaybackSpeed= */
C
.
RATE_UNSET
,
/* maxPlaybackSpeed= */
C
.
RATE_UNSET
));
float
adjustedSpeed1
=
defaultLivePlaybackSpeedControl
.
getAdjustedPlaybackSpeed
(
/* liveOffsetUs= */
1_500_000
);
defaultLivePlaybackSpeedControl
.
setLiveConfiguration
(
new
LiveConfiguration
(
/* targetLiveOffsetMs= */
1_000
,
/* minLiveOffsetMs= */
C
.
TIME_UNSET
,
/* maxLiveOffsetMs= */
C
.
TIME_UNSET
,
/* minPlaybackSpeed= */
C
.
RATE_UNSET
,
/* maxPlaybackSpeed= */
C
.
RATE_UNSET
));
float
adjustedSpeed2
=
defaultLivePlaybackSpeedControl
.
getAdjustedPlaybackSpeed
(
/* liveOffsetUs= */
2_500_000
);
assertThat
(
adjustedSpeed1
).
isNotEqualTo
(
adjustedSpeed2
);
}
...
...
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