Плагин webview_flutter не может воспроизводить некоторые вставленные на YouTube видео, которые работают, если воспроизводятся из веб-приложения. Видео отображает «Видео недоступно». Проигрывание видео на YouTube в приложении Flutter было проблемой не менее года.
https://github.com/flutter/flutter/issues/13756
Я пробовал различные плагины Flutter для воспроизведения встроенного видео на YouTube, но они либо поддерживают только Android, либо не работают с YouTube.
Я пытался использовать HTML-строку (YouTube iframe) непосредственно внутри плагина WebView, но видео недоступно. Загрузка HTML с веб-сервера позволяет воспроизводить некоторые видео, которые иначе не были бы непосредственно в приложении флаттера, например. Некоторые музыкальные клипы отображают «Видео недоступно. Это видео содержит материалы от Vevo, который заблокировал их показ на веб-сайте или в приложении».
Но если я запускаю то же видео с помощью API iframe YouTube (см. Код) из веб-приложения, оно работает без ошибок, т. Е. Встраивание не отключено, но эти видео не воспроизводятся в приложении Flutter. Я также читал похожие проблемы с воспроизведением видео на YouTube в Android, где предлагалось использовать WebChromeClient, который недоступен во Flutter.
Приложение Flutter, которое отображает видео YouTube внутри плагина WebView.
import 'package:flutter/material.dart';
import 'package:webview_flutter/webview_flutter.dart';
// Use IP instead of localhost to access local webserver
const _youTubeUrl = 'http://localhost:8080';
void main() => runApp(MyApp());
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'YouTube Video',
theme: ThemeData(
primarySwatch: Colors.blue,
),
home: MyHomePage(title: 'YouTube Video'),
);
}
}
class MyHomePage extends StatefulWidget {
final String title;
MyHomePage({Key key, this.title}) : super(key: key);
@override
_MyHomePageState createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
WebViewController _controller;
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text(widget.title),
),
body: Column(
children: <Widget>[
Expanded(
child: WebView(
initialUrl: '$_youTubeUrl/videos/IyFZznAk69U',
javascriptMode: JavascriptMode.unrestricted,
onWebViewCreated: (WebViewController controller) =>
_controller = controller,
),
),
],
),
floatingActionButton: FloatingActionButton(
child: Icon(Icons.play_arrow),
onPressed: () async {
await _controller.evaluateJavascript('player.loadVideoById("d_m5csmrf7I")');
},
),
);
}
}
Код на стороне сервера Node.js, который возвращает index.html через экспресс-маршрутизацию
const path = require("path");
const express = require("express");
const server = express();
// Define route
api.get("/", (req, res) =>
res.sendFile(path.join(__dirname + "/index.html"))
);
const port = process.env.PORT || 8080;
server.listen(port, () => console.log(`Server listening on ${port}`));
process.on("exit", () => console.log("Server exited"));
index.html файл, который использует API iframe YouTube для приложения Flutter
<!DOCTYPE html>
<html>
<head>
<style>
#player {
position: relative;
padding-top: 56.25%;
min-width: 240px;
height: 0;
}
iframe {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
}
</style>
<script>
var player;
function onYouTubeIframeAPIReady() {
player = new YT.Player("yt", {
videoId: "IyFZznAk69U",
playerVars: {
autoplay: 1
}
});
}
</script>
<script src="https://www.youtube.com/iframe_api" async></script>
</head>
<body>
<div id="player">
<div id="yt"></div>
</div>
</body>
</html>