Skip to content
This repository has been archived by the owner on Nov 7, 2023. It is now read-only.

Commit

Permalink
feat: show loading when player is buffering
Browse files Browse the repository at this point in the history
  • Loading branch information
KyleKun committed Oct 22, 2021
1 parent 40a5241 commit 5327c6a
Show file tree
Hide file tree
Showing 6 changed files with 125 additions and 8 deletions.
2 changes: 2 additions & 0 deletions lib/core/models/player.dart
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ enum PlayerEvents {
durationUpdate,
play,
pause,
buffering,
seek,
volume,
end,
Expand Down Expand Up @@ -51,6 +52,7 @@ abstract class Player extends Eventer<PlayerEvent> {
}

bool get isPlaying;
bool get isBuffering;
Duration? get duration;
Duration? get totalDuration;
int get volume;
Expand Down
31 changes: 24 additions & 7 deletions lib/pages/anime_page/watch_page.dart
Original file line number Diff line number Diff line change
@@ -1,13 +1,16 @@
import 'dart:async';
import 'dart:convert';

import 'package:extensions/extensions.dart' as extensions;
import 'package:flutter/gestures.dart';
import 'package:flutter/material.dart';

import './select_source.dart';
import '../../config.dart';
import '../../core/models/player.dart' as player_model;
import '../../core/models/tracker_provider.dart';
import '../../core/trackers/providers.dart';
import '../../plugins/helpers/double_value_listenable_builder.dart';
import '../../plugins/helpers/screen.dart';
import '../../plugins/helpers/stateful_holder.dart';
import '../../plugins/helpers/ui.dart';
Expand Down Expand Up @@ -77,6 +80,7 @@ class WatchPageState extends State<WatchPage>
final Duration animationDuration = const Duration(milliseconds: 300);

final ValueNotifier<bool> isPlaying = ValueNotifier<bool>(false);
final ValueNotifier<bool> isBuffering = ValueNotifier<bool>(true);
late AnimationController playPauseController;
late AnimationController overlayController;

Expand Down Expand Up @@ -262,6 +266,10 @@ class WatchPageState extends State<WatchPage>
speed = player!.speed;
break;

case player_model.PlayerEvents.buffering:
isBuffering.value = player!.isBuffering;
break;

case player_model.PlayerEvents.error:
showDialog(
context: context,
Expand Down Expand Up @@ -667,19 +675,28 @@ class WatchPageState extends State<WatchPage>
color: Colors.white,
),
),
ValueListenableBuilder<bool>(
valueListenable: isPlaying,
DoubleValueListenableBuilder<
bool, bool>(
valueListenable1: isPlaying,
valueListenable2:
isBuffering,
builder: (
final BuildContext
context,
final bool isPlaying,
final bool isBuffering,
final Widget? child,
) {
isPlaying
? playPauseController
.forward()
: playPauseController
.reverse();
if (isBuffering &&
isPlaying) {
return loader;
} else {
isPlaying
? playPauseController
.forward()
: playPauseController
.reverse();
}
return Material(
type: MaterialType
.transparency,
Expand Down
81 changes: 81 additions & 0 deletions lib/plugins/helpers/double_value_listenable_builder.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,81 @@
import 'package:flutter/foundation.dart';
import 'package:flutter/widgets.dart';

typedef DoubleValueWidgetBuilder<T, T2> = Widget Function(
BuildContext context,
T value1,
T2 value2,
Widget? child,
);

class DoubleValueListenableBuilder<T, T2> extends StatefulWidget {
const DoubleValueListenableBuilder({
required final this.valueListenable1,
required final this.valueListenable2,
required final this.builder,
final this.child,
final Key? key,
}) : super(key: key);

final ValueListenable<T> valueListenable1;
final ValueListenable<T2> valueListenable2;
final DoubleValueWidgetBuilder<T, T2> builder;
final Widget? child;

@override
State<StatefulWidget> createState() =>
_DoubleValueListenableBuilderState<T, T2>();
}

class _DoubleValueListenableBuilderState<T, T2>
extends State<DoubleValueListenableBuilder<T, T2>> {
late T value1;
late T2 value2;

@override
void initState() {
super.initState();
value1 = widget.valueListenable1.value;
value2 = widget.valueListenable2.value;
widget.valueListenable1.addListener(_valueChanged1);
widget.valueListenable2.addListener(_valueChanged2);
}

@override
void didUpdateWidget(final DoubleValueListenableBuilder<T, T2> oldWidget) {
if (oldWidget.valueListenable1 != widget.valueListenable1 &&
oldWidget.valueListenable2 != widget.valueListenable2) {
oldWidget.valueListenable1.removeListener(_valueChanged1);
value1 = widget.valueListenable1.value;
widget.valueListenable1.addListener(_valueChanged1);

oldWidget.valueListenable2.removeListener(_valueChanged2);
value2 = widget.valueListenable2.value;
widget.valueListenable2.addListener(_valueChanged2);
}
super.didUpdateWidget(oldWidget);
}

@override
void dispose() {
widget.valueListenable1.removeListener(_valueChanged1);
widget.valueListenable2.removeListener(_valueChanged2);
super.dispose();
}

void _valueChanged1() {
setState(() {
value1 = widget.valueListenable1.value;
});
}

void _valueChanged2() {
setState(() {
value2 = widget.valueListenable2.value;
});
}

@override
Widget build(final BuildContext context) =>
widget.builder(context, value1, value2, widget.child);
}
2 changes: 1 addition & 1 deletion lib/plugins/translator/translations/pt_br.dart
Original file line number Diff line number Diff line change
Expand Up @@ -332,7 +332,7 @@ class Sentences extends en.Sentences {
String topAnimes() => 'Top Animes';

@override
String recentlyUpdated() => 'Atualizado recentemente';
String recentlyUpdated() => 'Atualizados recentemente';

@override
String recommendedBy(final String by) => 'Recomendado por $by';
Expand Down
7 changes: 7 additions & 0 deletions lib/plugins/video_player/better_player.dart
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,10 @@ class BetterPlayer extends model.Player {
dispatch(model.PlayerEvent(model.PlayerEvents.speed, null));
break;

case better_player.BetterPlayerEventType.bufferingUpdate:
dispatch(model.PlayerEvent(model.PlayerEvents.buffering, null));
break;

case better_player.BetterPlayerEventType.exception:
dispatch(
model.PlayerEvent(model.PlayerEvents.error, e.parameters),
Expand Down Expand Up @@ -123,6 +127,9 @@ class BetterPlayer extends model.Player {
@override
bool get isPlaying => _controller.isPlaying() ?? false;

@override
bool get isBuffering => _controller.isBuffering() ?? true;

@override
Duration? get duration => _controller.videoPlayerController?.value.position;

Expand Down
10 changes: 10 additions & 0 deletions lib/plugins/video_player/dart_vlc.dart
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ class DartVlc extends model.Player {

double? _prevSpeed;
double? _prevVolume;
double? _prevBuffering;
final GlobalKey _playerKey = GlobalKey();

final List<StreamSubscription<dynamic>> _subscriptions =
Expand Down Expand Up @@ -55,6 +56,12 @@ class DartVlc extends model.Player {
ready = true;
}
}),
_player.bufferingProgressStream
.listen((final double bufferingProgress) {
if (_prevBuffering != bufferingProgress) {
dispatch(model.PlayerEvent(model.PlayerEvents.buffering, null));
}
})
],
);

Expand Down Expand Up @@ -116,6 +123,9 @@ class DartVlc extends model.Player {
@override
bool get isPlaying => _player.playback.isPlaying;

@override
bool get isBuffering => _player.bufferingProgress < 100.0;

@override
Duration? get duration => _player.position.position;

Expand Down

0 comments on commit 5327c6a

Please sign in to comment.