-
Notifications
You must be signed in to change notification settings - Fork 10
Expand file tree
/
Copy pathtimebased_state.dart
More file actions
92 lines (76 loc) · 3.43 KB
/
timebased_state.dart
File metadata and controls
92 lines (76 loc) · 3.43 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
import 'package:meta/meta.dart';
import 'enums.dart';
import 'shared/publication/locator.dart';
import 'utils/jsonable.dart';
@immutable
class ReadiumTimebasedState implements JSONable {
const ReadiumTimebasedState({
required this.state,
this.currentOffset,
this.currentBuffered,
this.currentDuration,
this.currentLocator,
});
factory ReadiumTimebasedState.fromJson(final Map<String, dynamic> map) {
final jsonObject = Map<String, dynamic>.of(map);
final state = TimebasedState.fromString(jsonObject.optString('state', remove: true));
final currentOffset = jsonObject.optNullableInt('currentOffset', remove: true);
final currentBuffered = jsonObject.optNullableInt('currentBuffered', remove: true);
final currentDuration = jsonObject.optNullableInt('currentDuration', remove: true);
var currentLocator = Locator.fromJsonDynamic(jsonObject.opt('currentLocator', remove: true));
if (state == TimebasedState.ended && currentLocator != null) {
// Workaround rounding error from native layer.
// Sometimes progression and totalProgression are very close to 1.0 but not exactly, which causes confusion for
// the UI.
currentLocator = currentLocator.copyWithLocations(
progression: currentLocator.locations?.progression?.roundToIfCloseTo(1.0, epsilon: 0.01) ?? 1.0,
totalProgression: currentLocator.locations?.totalProgression?.roundToIfCloseTo(1.0) ?? 1.0,
);
}
return ReadiumTimebasedState(
state: state,
currentOffset: currentOffset != null ? Duration(milliseconds: currentOffset) : null,
currentBuffered: currentBuffered != null ? Duration(milliseconds: currentBuffered) : null,
currentDuration: currentDuration != null ? Duration(milliseconds: currentDuration) : null,
currentLocator: currentLocator,
);
}
@override
String toString() =>
'ReadiumTimebasedState($state,offset=$currentOffset,duration=$currentDuration,buffered=$currentBuffered,'
'href=${currentLocator?.href},'
'progression=${currentLocator?.locations?.progression},'
'totalProgression=${currentLocator?.locations?.totalProgression}),'
'title=${currentLocator?.title}),'
'chapterPosition=${currentLocator?.locations?.position})';
/// Current time-based player state.
final TimebasedState state;
/// Playback offset in the current audio file.
final Duration? currentOffset;
/// Duration buffered of the current file.
final Duration? currentBuffered;
/// Total duration of the current file.
final Duration? currentDuration;
/// Current Locator in the publication being played.
final Locator? currentLocator;
@override
Map<String, dynamic> toJson() => {}
..put('state', state.name)
..putOpt('currentOffset', currentOffset?.inMilliseconds)
..putOpt('currentBuffered', currentBuffered?.inMilliseconds)
..putOpt('currentDuration', currentDuration?.inMilliseconds)
..putOpt('currentLocator', currentLocator?.toJson());
ReadiumTimebasedState copyWith({
TimebasedState? state,
Duration? currentOffset,
Duration? currentBuffered,
Duration? currentDuration,
Locator? currentLocator,
}) => ReadiumTimebasedState(
state: state ?? this.state,
currentOffset: currentOffset ?? this.currentOffset,
currentBuffered: currentBuffered ?? this.currentBuffered,
currentDuration: currentDuration ?? this.currentDuration,
currentLocator: currentLocator ?? this.currentLocator,
);
}