#180 video: double tap play gesture
This commit is contained in:
parent
3a91314a5d
commit
6b62806ddb
7 changed files with 52 additions and 10 deletions
|
@ -643,6 +643,7 @@
|
|||
|
||||
"settingsGesturesTile": "Gestures",
|
||||
"settingsGesturesTitle": "Gestures",
|
||||
"settingsVideoGestureDoubleTapTogglePlay": "Double tap to play/pause",
|
||||
"settingsVideoGestureSideDoubleTapSeek": "Double tap on screen edges to seek backward/forward",
|
||||
|
||||
"settingsSectionPrivacy": "Privacy",
|
||||
|
|
|
@ -82,6 +82,7 @@ class SettingsDefaults {
|
|||
static const enableVideoAutoPlay = false;
|
||||
static const videoLoopMode = VideoLoopMode.shortOnly;
|
||||
static const videoShowRawTimedText = false;
|
||||
static const videoGestureDoubleTapTogglePlay = false;
|
||||
static const videoGestureSideDoubleTapSeek = true;
|
||||
|
||||
// subtitles
|
||||
|
|
|
@ -95,6 +95,7 @@ class Settings extends ChangeNotifier {
|
|||
static const enableVideoAutoPlayKey = 'video_auto_play';
|
||||
static const videoLoopModeKey = 'video_loop';
|
||||
static const videoShowRawTimedTextKey = 'video_show_raw_timed_text';
|
||||
static const videoGestureDoubleTapTogglePlayKey = 'video_gesture_double_tap_toggle_play';
|
||||
static const videoGestureSideDoubleTapSeekKey = 'video_gesture_side_double_tap_skip';
|
||||
|
||||
// subtitles
|
||||
|
@ -437,6 +438,10 @@ class Settings extends ChangeNotifier {
|
|||
|
||||
set videoShowRawTimedText(bool newValue) => setAndNotify(videoShowRawTimedTextKey, newValue);
|
||||
|
||||
bool get videoGestureDoubleTapTogglePlay => getBoolOrDefault(videoGestureDoubleTapTogglePlayKey, SettingsDefaults.videoGestureDoubleTapTogglePlay);
|
||||
|
||||
set videoGestureDoubleTapTogglePlay(bool newValue) => setAndNotify(videoGestureDoubleTapTogglePlayKey, newValue);
|
||||
|
||||
bool get videoGestureSideDoubleTapSeek => getBoolOrDefault(videoGestureSideDoubleTapSeekKey, SettingsDefaults.videoGestureSideDoubleTapSeek);
|
||||
|
||||
set videoGestureSideDoubleTapSeek(bool newValue) => setAndNotify(videoGestureSideDoubleTapSeekKey, newValue);
|
||||
|
@ -659,6 +664,7 @@ class Settings extends ChangeNotifier {
|
|||
case enableMotionPhotoAutoPlayKey:
|
||||
case enableVideoHardwareAccelerationKey:
|
||||
case enableVideoAutoPlayKey:
|
||||
case videoGestureDoubleTapTogglePlayKey:
|
||||
case videoGestureSideDoubleTapSeekKey:
|
||||
case subtitleShowOutlineKey:
|
||||
case saveSearchHistoryKey:
|
||||
|
|
|
@ -39,7 +39,7 @@ class Durations {
|
|||
static const thumbnailScrollerScrollAnimation = Duration(milliseconds: 200);
|
||||
static const thumbnailScrollerShadeAnimation = Duration(milliseconds: 150);
|
||||
static const viewerVideoPlayerTransition = Duration(milliseconds: 500);
|
||||
static const viewerActionFeedbackAnimation = Duration(milliseconds: 800);
|
||||
static const viewerActionFeedbackAnimation = Duration(milliseconds: 600);
|
||||
|
||||
// info animations
|
||||
static const mapStyleSwitchAnimation = Duration(milliseconds: 300);
|
||||
|
|
|
@ -37,6 +37,14 @@ class VideoGesturesPage extends StatelessWidget {
|
|||
body: SafeArea(
|
||||
child: ListView(
|
||||
children: [
|
||||
Selector<Settings, bool>(
|
||||
selector: (context, s) => s.videoGestureDoubleTapTogglePlay,
|
||||
builder: (context, current, child) => SwitchListTile(
|
||||
value: current,
|
||||
onChanged: (v) => settings.videoGestureDoubleTapTogglePlay = v,
|
||||
title: Text(context.l10n.settingsVideoGestureDoubleTapTogglePlay),
|
||||
),
|
||||
),
|
||||
Selector<Settings, bool>(
|
||||
selector: (context, s) => s.videoGestureSideDoubleTapSeek,
|
||||
builder: (context, current, child) => SwitchListTile(
|
||||
|
|
|
@ -6,7 +6,7 @@ import 'package:aves/model/entry_images.dart';
|
|||
import 'package:aves/model/settings/enums/accessibility_animations.dart';
|
||||
import 'package:aves/model/settings/settings.dart';
|
||||
import 'package:aves/theme/durations.dart';
|
||||
import 'package:aves/utils/constants.dart';
|
||||
import 'package:aves/theme/icons.dart';
|
||||
import 'package:aves/widgets/common/action_mixins/feedback.dart';
|
||||
import 'package:aves/widgets/common/magnifier/controller/controller.dart';
|
||||
import 'package:aves/widgets/common/magnifier/controller/state.dart';
|
||||
|
@ -193,17 +193,27 @@ class _EntryPageViewState extends State<EntryPageView> {
|
|||
final videoController = context.read<VideoConductor>().getController(entry);
|
||||
if (videoController == null) return const SizedBox();
|
||||
|
||||
Positioned _buildDoubleTapDetector(AlignmentGeometry alignment, VideoAction action) {
|
||||
Positioned _buildDoubleTapDetector(
|
||||
VideoAction action, {
|
||||
double widthFactor = 1,
|
||||
AlignmentGeometry alignment = Alignment.center,
|
||||
IconData? Function()? icon,
|
||||
}) {
|
||||
return Positioned.fill(
|
||||
child: FractionallySizedBox(
|
||||
alignment: alignment,
|
||||
widthFactor: .25,
|
||||
widthFactor: widthFactor,
|
||||
child: GestureDetector(
|
||||
onDoubleTap: () {
|
||||
_actionFeedbackChildNotifier.value = DecoratedIcon(
|
||||
action.getIconData(),
|
||||
shadows: Constants.embossShadows,
|
||||
icon?.call() ?? action.getIconData(),
|
||||
size: 48,
|
||||
shadows: const [
|
||||
Shadow(
|
||||
color: Colors.black,
|
||||
blurRadius: 4,
|
||||
)
|
||||
],
|
||||
);
|
||||
VideoGestureNotification(
|
||||
controller: videoController,
|
||||
|
@ -219,6 +229,9 @@ class _EntryPageViewState extends State<EntryPageView> {
|
|||
valueListenable: videoController.sarNotifier,
|
||||
builder: (context, sar, child) {
|
||||
final videoDisplaySize = entry.videoDisplaySize(sar);
|
||||
final playGesture = settings.videoGestureDoubleTapTogglePlay;
|
||||
final seekGesture = settings.videoGestureSideDoubleTapSeek;
|
||||
final useActionGesture = playGesture || seekGesture;
|
||||
return Stack(
|
||||
fit: StackFit.expand,
|
||||
children: [
|
||||
|
@ -241,16 +254,22 @@ class _EntryPageViewState extends State<EntryPageView> {
|
|||
viewStateNotifier: _viewStateNotifier,
|
||||
debugMode: true,
|
||||
),
|
||||
if (settings.videoGestureSideDoubleTapSeek) ...[
|
||||
_buildDoubleTapDetector(Alignment.centerLeft, VideoAction.replay10),
|
||||
_buildDoubleTapDetector(Alignment.centerRight, VideoAction.skip10),
|
||||
if (playGesture)
|
||||
_buildDoubleTapDetector(
|
||||
VideoAction.togglePlay,
|
||||
icon: () => videoController.isPlaying ? AIcons.pause : AIcons.play,
|
||||
),
|
||||
if (seekGesture) ...[
|
||||
_buildDoubleTapDetector(VideoAction.replay10, widthFactor: .25, alignment: Alignment.centerLeft),
|
||||
_buildDoubleTapDetector(VideoAction.skip10, widthFactor: .25, alignment: Alignment.centerRight),
|
||||
],
|
||||
if (useActionGesture)
|
||||
ValueListenableBuilder<Widget?>(
|
||||
valueListenable: _actionFeedbackChildNotifier,
|
||||
builder: (context, feedbackChild, child) => ActionFeedback(
|
||||
child: feedbackChild,
|
||||
),
|
||||
),
|
||||
],
|
||||
],
|
||||
),
|
||||
_buildVideoCover(videoController, videoDisplaySize),
|
||||
|
|
|
@ -4,6 +4,7 @@
|
|||
"settingsViewerShowOverlayThumbnails",
|
||||
"settingsGesturesTile",
|
||||
"settingsGesturesTitle",
|
||||
"settingsVideoGestureDoubleTapTogglePlay",
|
||||
"settingsVideoGestureSideDoubleTapSeek"
|
||||
],
|
||||
|
||||
|
@ -11,6 +12,7 @@
|
|||
"settingsViewerShowOverlayThumbnails",
|
||||
"settingsGesturesTile",
|
||||
"settingsGesturesTitle",
|
||||
"settingsVideoGestureDoubleTapTogglePlay",
|
||||
"settingsVideoGestureSideDoubleTapSeek"
|
||||
],
|
||||
|
||||
|
@ -18,6 +20,7 @@
|
|||
"settingsViewerShowOverlayThumbnails",
|
||||
"settingsGesturesTile",
|
||||
"settingsGesturesTitle",
|
||||
"settingsVideoGestureDoubleTapTogglePlay",
|
||||
"settingsVideoGestureSideDoubleTapSeek"
|
||||
],
|
||||
|
||||
|
@ -25,6 +28,7 @@
|
|||
"settingsViewerShowOverlayThumbnails",
|
||||
"settingsGesturesTile",
|
||||
"settingsGesturesTitle",
|
||||
"settingsVideoGestureDoubleTapTogglePlay",
|
||||
"settingsVideoGestureSideDoubleTapSeek"
|
||||
],
|
||||
|
||||
|
@ -32,6 +36,7 @@
|
|||
"settingsViewerShowOverlayThumbnails",
|
||||
"settingsGesturesTile",
|
||||
"settingsGesturesTitle",
|
||||
"settingsVideoGestureDoubleTapTogglePlay",
|
||||
"settingsVideoGestureSideDoubleTapSeek"
|
||||
],
|
||||
|
||||
|
@ -39,6 +44,7 @@
|
|||
"settingsViewerShowOverlayThumbnails",
|
||||
"settingsGesturesTile",
|
||||
"settingsGesturesTitle",
|
||||
"settingsVideoGestureDoubleTapTogglePlay",
|
||||
"settingsVideoGestureSideDoubleTapSeek"
|
||||
],
|
||||
|
||||
|
@ -47,6 +53,7 @@
|
|||
"settingsViewerShowOverlayThumbnails",
|
||||
"settingsGesturesTile",
|
||||
"settingsGesturesTitle",
|
||||
"settingsVideoGestureDoubleTapTogglePlay",
|
||||
"settingsVideoGestureSideDoubleTapSeek"
|
||||
]
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue