Skip to content

Commit

Permalink
Merge pull request #31 from miru-project/feat/external-video-player
Browse files Browse the repository at this point in the history
Feat external player
  • Loading branch information
MiaoMint authored Aug 29, 2023
2 parents d513b85 + c38df32 commit 5b2af66
Show file tree
Hide file tree
Showing 9 changed files with 139 additions and 2 deletions.
5 changes: 5 additions & 0 deletions assets/i18n/en.json
Original file line number Diff line number Diff line change
Expand Up @@ -88,6 +88,9 @@
"theme-dark": "Dark",
"nsfw": "NSFW",
"nsfw-subtitle": "Show NSFW content",
"external-player": "Preferred video player",
"external-player-subtitle": "Currently, the preferred player is {player}",
"external-player-builtin": "Built-in",
"language-subtitle": "Change the language of the software",
"extension-log": "Extension Log Window",
"extension-log-subtitle": "Used for debugging extensions",
Expand All @@ -100,6 +103,8 @@
"license-subtitle": "License"
},

"external-player-launching": "Launching {player}",

"detail": {
"favorite": "Favorite",
"favorited": "Favorited",
Expand Down
5 changes: 5 additions & 0 deletions assets/i18n/zh.json
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,9 @@
"theme-dark": "深色",
"nsfw": "NSFW",
"nsfw-subtitle": "显示 NSFW 内容",
"external-player": "优先使用的视频播放器",
"external-player-subtitle": "当前优先使用的是 {player}",
"external-player-builtin": "内置播放器",
"language-subtitle": "选择软件的语言",
"extension-log": "扩展日志窗口",
"extension-log-subtitle": "用于调试扩展",
Expand All @@ -89,6 +92,8 @@
"license-subtitle": "许可证"
},

"external-player-launching": "正在启动 {player}",

"detail": {
"favorite": "收藏",
"favorited": "已收藏",
Expand Down
46 changes: 45 additions & 1 deletion lib/pages/detail/controller.dart
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ import 'package:miru_app/router/router.dart';
import 'package:miru_app/utils/database.dart';
import 'package:miru_app/utils/extension.dart';
import 'package:miru_app/utils/extension_runtime.dart';
import 'package:miru_app/utils/external_player.dart';
import 'package:miru_app/utils/i18n.dart';
import 'package:miru_app/utils/miru_directory.dart';
import 'package:miru_app/utils/miru_storage.dart';
Expand Down Expand Up @@ -307,7 +308,7 @@ class DetailPageController extends GetxController {
List<ExtensionEpisode> urls,
int index,
int selectEpGroup,
) {
) async {
if (runtime.value == null) {
showPlatformSnackbar(
context: cuurentContext,
Expand All @@ -323,6 +324,49 @@ class DetailPageController extends GetxController {
return;
}

if (type == ExtensionType.bangumi) {
final player = MiruStorage.getSetting(SettingKey.videoPlayer);

if (player != 'built-in') {
showPlatformSnackbar(
context: cuurentContext,
content: FlutterI18n.translate(
cuurentContext,
'external-player-launching',
translationParams: {
'player': player,
},
),
);
late ExtensionBangumiWatch watchData;
try {
watchData = await runtime.value!.watch(urls[index].url)
as ExtensionBangumiWatch;
} catch (e) {
showPlatformSnackbar(
context: cuurentContext,
content: e.toString().split('\n')[0],
severity: fluent.InfoBarSeverity.error,
);
return;
}
try {
if (GetPlatform.isMobile) {
await launchMobileExternalPlayer(watchData.url, player);
return;
}
await launchDesktopExternalPlayer(watchData.url, player);
return;
} catch (e) {
showPlatformSnackbar(
context: cuurentContext,
content: e.toString().split('\n')[0],
severity: fluent.InfoBarSeverity.error,
);
}
}
}

Navigator.of(context, rootNavigator: true).push(
PageRouteBuilder(
transitionDuration: const Duration(milliseconds: 600),
Expand Down
1 change: 0 additions & 1 deletion lib/pages/detail/view.dart
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,6 @@ import 'package:get/get.dart';
import 'package:miru_app/api/tmdb.dart';
import 'package:miru_app/models/extension.dart';
import 'package:miru_app/pages/detail/controller.dart';
import 'package:miru_app/pages/detail/pages/tmdb_binding.dart';
import 'package:miru_app/pages/detail/pages/webview.dart';
import 'package:miru_app/pages/detail/widgets/detail_appbar_flexible_space.dart';
import 'package:miru_app/pages/detail/widgets/detail_appbar_title.dart';
Expand Down
35 changes: 35 additions & 0 deletions lib/pages/settings/view.dart
Original file line number Diff line number Diff line change
Expand Up @@ -204,6 +204,41 @@ class _SettingsPageState extends State<SettingsPage> {
},
),
const SizedBox(height: 8),
SettingsRadiosTile(
icon: const PlatformWidget(
androidWidget: Icon(Icons.play_arrow),
desktopWidget: Icon(fluent.FluentIcons.play_resume, size: 24),
),
title: 'settings.external-player'.i18n,
itemNameValue: () {
if (Platform.isAndroid) {
return {
"settings.external-player-builtin".i18n: "built-in",
"VLC": "vlc",
"Other": "other",
};
}
return {
"settings.external-player-builtin".i18n: "built-in",
"VLC": "vlc",
"PotPlayer": "potplayer",
};
}(),
buildSubtitle: () => FlutterI18n.translate(
context,
'settings.external-player-subtitle',
translationParams: {
'player': MiruStorage.getSetting(SettingKey.videoPlayer),
},
),
applyValue: (value) {
MiruStorage.setSetting(SettingKey.videoPlayer, value);
},
buildGroupValue: () {
return MiruStorage.getSetting(SettingKey.videoPlayer);
},
),
const SizedBox(height: 8),
if (!Platform.isAndroid)
Obx(
() {
Expand Down
38 changes: 38 additions & 0 deletions lib/utils/external_player.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
import 'dart:io';

import 'package:android_intent_plus/android_intent.dart';
import 'package:url_launcher/url_launcher_string.dart';

Future<void> launchMobileExternalPlayer(String playUrl, String player) async {
switch (player) {
case "vlc":
await _launchExternalPlayer("vlc://$playUrl");
break;
case "other":
await AndroidIntent(
action: 'action_view',
data: playUrl,
type: 'video/*',
).launch();
break;
}
}

// desktop
Future<void> launchDesktopExternalPlayer(String playUrl, String player) async {
switch (player) {
case "vlc":
const vlc = 'C:\\Program Files\\VideoLAN\\VLC\\vlc.exe';
await Process.run(vlc, [playUrl]);
break;
case "potplayer":
await _launchExternalPlayer("potplayer://$playUrl");
break;
}
}

_launchExternalPlayer(String url) async {
if (!await launchUrlString(url, mode: LaunchMode.externalApplication)) {
throw Exception("Failed to launch $url");
}
}
2 changes: 2 additions & 0 deletions lib/utils/miru_storage.dart
Original file line number Diff line number Diff line change
Expand Up @@ -111,6 +111,7 @@ class MiruStorage {
await _initSetting(SettingKey.novelFontSize, 18.0);
await _initSetting(SettingKey.theme, 'system');
await _initSetting(SettingKey.enableNSFW, false);
await _initSetting(SettingKey.videoPlayer, 'built-in');
}

static _initSetting(String key, dynamic value) async {
Expand All @@ -136,5 +137,6 @@ class SettingKey {
static String language = 'Language';
static String novelFontSize = 'NovelFontSize';
static String enableNSFW = 'EnableNSFW';
static String videoPlayer = 'VideoPlayer';
static String databaseVersion = 'DatabaseVersion';
}
8 changes: 8 additions & 0 deletions pubspec.lock
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,14 @@ packages:
url: "https://pub.dev"
source: hosted
version: "5.13.0"
android_intent_plus:
dependency: "direct main"
description:
name: android_intent_plus
sha256: f72ae20bb37108694f442e7ae6acbd28b453ca62ce86842f6787b784355abfe6
url: "https://pub.dev"
source: hosted
version: "4.0.2"
archive:
dependency: transitive
description:
Expand Down
1 change: 1 addition & 0 deletions pubspec.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -52,6 +52,7 @@ dependencies:
http_parser: ^4.0.2
html: ^0.15.4
xpath_selector_html_parser: ^3.0.1
android_intent_plus: ^4.0.2

dev_dependencies:
flutter_test:
Expand Down

0 comments on commit 5b2af66

Please sign in to comment.