[英]How to support video streaming from ESP32CAM using flutter video_player plugin?
[英]How to pause flutter video(video_player plugin) when navigating from page to another
我正在使用 flutter video_player( https://pub.dartlang.org/packages/video_player ) 插件来播放视频。 但是当我在颤动中从一页导航到另一页时,视频仍在播放。 从任何其他应用程序播放音乐时,我遇到了同样的问题(例如:播放颤动视频时从通知中播放音乐)。 我怎样才能暂停它?
编辑:第二个选项:所以我想出了另一个解决方案。 VisibilityDetector
是一个“小部件”,它可以包装任何其他小部件并在小部件的可见区域发生变化时发出通知。
VisibilityDetector(
key: Key("unique key"),
onVisibilityChanged: (VisibilityInfo info) {
debugPrint("${info.visibleFraction} of my widget is visible");
if(info.visibleFraction == 0){
videoPlayerController.pause();
}
else{
videoPlayerController.play();
}
},
child: VideoPlayer());
)
第一个选项:通过使用RouteObserver
和RouteAware
您的小部件将在另一个屏幕被推到它上面或它被RouteAware
回顶部时收到通知。
首先,您需要将RouteObserver
添加到MaterialApp
或您的Navigator
。
RouteObserver<PageRoute> routeObserver = RouteObserver<PageRoute>();
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Demo',
navigatorObservers: [routeObserver], //HERE
theme: ThemeData(
primarySwatch: Colors.blue,
),
home: MyHomePage(title: 'Flutter Demo Home Page'),
);
}
}
然后您必须将RouteAware
mixin 添加到您的小部件,并将其订阅到RouteObserver
。
class VideoPlayerItem extends StatefulWidget {
final File file;
VideoPlayerItem(this.file);
@override
_VideoPlayerItemState createState() => _VideoPlayerItemState();
}
class _VideoPlayerItemState extends State<VideoPlayerItem> with RouteAware {
VideoPlayerController _videoPlayerController;
@override
void initState() {
super.initState();
_videoPlayerController = VideoPlayerController.file(widget.file);
_videoPlayerController.initialize().then((_) {
if (mounted) {
setState(() {});
_videoPlayerController.play();
}
});
}
@override
void didChangeDependencies() {
routeObserver.subscribe(this, ModalRoute.of(context));//Subscribe it here
super.didChangeDependencies();
}
/// Called when the current route has been popped off.
@override
void didPop() {
print("didPop");
super.didPop();
}
/// Called when the top route has been popped off, and the current route
/// shows up.
@override
void didPopNext() {
print("didPopNext");
_videoPlayerController.play();
super.didPopNext();
}
/// Called when the current route has been pushed.
@override
void didPush() {
print("didPush");
super.didPush();
}
/// Called when a new route has been pushed, and the current route is no
/// longer visible.
@override
void didPushNext() {
print("didPushNext");
_videoPlayerController.pause();
super.didPushNext();
}
@override
Widget build(BuildContext context) {
return _videoPlayerController?.value?.initialized ?? false
? AspectRatio(
aspectRatio: _videoPlayerController.value.aspectRatio,
child: VideoPlayer(_videoPlayerController),
)
: Container();
}
@override
void dispose() {
routeObserver.unsubscribe(this); //Don't forget to unsubscribe it!!!!!!
super.dispose();
_videoPlayerController.dispose();
}
}
或者您可以override
视频播放器小部件的dispose
方法:
@override
void dispose() {
super.dispose();
_controller.pause();
}
您可以通过重塑您的应用以使视频播放器小部件成为导航树中的最后一个来使此方法起作用,因此,每当您向后导航时,它都会自动暂停,播放器小部件会遇到很多问题。 我设法通过刚才提到的方法解决了这个特定问题
你有 - VideoPlayerController _controller;
在导航到其他屏幕之前 -
_controller.pause(); // add this
Navigator.push(
context, MaterialPageRoute(builder: (BuildContext context) => NextPage()));
或者
如果它是有状态小部件,那么您可以覆盖 - dispose()
方法。
@override
void dispose() {
super.dispose();
_controller.pause();
}
简单而且对我chewie
,我从chewie
示例代码中得到了这个: https : chewie
就在 onTap/onPressed 上使用 setState 并在这个 setState 中制作 videoController.pause 或 dispose,无论你想要什么。
onTap:() {
setState(() {
widget.videoController.pause();
Navigator.of(context)
.pushNamed(YOUR-NAVIGATION-PAGE-NAME);
});
},
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.