feat: 逻辑与页面布局分离

This commit is contained in:
Vicky committed 2026-10-13 16:52:14 +08:00
1 parent b1f6ce4bf9
commit 1e61ae7a0b
11 files changed
+1233 -907

No files matched your search

+24 -11
View File
@@ -37,24 +37,30 @@ class SeekProgressBar extends StatefulWidget {
}
class _SeekProgressBarState extends State<SeekProgressBar> {
double? _previewFraction;
final _previewFraction = ValueNotifier<double?>(null);
@override
void didUpdateWidget(covariant SeekProgressBar oldWidget) {
super.didUpdateWidget(oldWidget);
if (oldWidget.valueListenable != widget.valueListenable) {
_previewFraction = null;
_previewFraction.value = null;
}
}
@override
void dispose() {
_previewFraction.dispose();
super.dispose();
}
Future<void> _finish(double fraction, Duration duration) async {
final source = widget.valueListenable;
setState(() => _previewFraction = fraction);
_previewFraction.value = fraction;
try {
await widget.onSeek?.call(seekPositionForFraction(fraction, duration));
} finally {
if (mounted && widget.valueListenable == source) {
setState(() => _previewFraction = null);
_previewFraction.value = null;
}
}
}
@@ -63,11 +69,18 @@ class _SeekProgressBarState extends State<SeekProgressBar> {
Widget build(BuildContext context) {
final source = widget.valueListenable;
if (source == null) {
return _buildTrack(context, const VideoPlayerValue.uninitialized());
return ValueListenableBuilder<double?>(
valueListenable: _previewFraction,
builder: (context, _, _) =>
_buildTrack(context, const VideoPlayerValue.uninitialized()),
);
}
return ValueListenableBuilder<VideoPlayerValue>(
valueListenable: source,
builder: (context, value, _) => _buildTrack(context, value),
builder: (context, value, _) => ValueListenableBuilder<double?>(
valueListenable: _previewFraction,
builder: (context, _, _) => _buildTrack(context, value),
),
);
}
@@ -77,11 +90,11 @@ class _SeekProgressBarState extends State<SeekProgressBar> {
final played = total > 0
? (video.position.inMilliseconds / total).clamp(0.0, 1.0)
: 0.0;
final fraction = _previewFraction ?? played;
final previewPosition = _previewFraction == null
final fraction = _previewFraction.value ?? played;
final previewPosition = _previewFraction.value == null
? video.position
: seekPositionForFraction(fraction, video.duration);
final scrubbing = _previewFraction != null;
final scrubbing = _previewFraction.value != null;
return Column(
mainAxisSize: MainAxisSize.min,
@@ -107,12 +120,12 @@ class _SeekProgressBarState extends State<SeekProgressBar> {
value: fraction,
onChangeStart: enabled
? (value) {
setState(() => _previewFraction = value);
_previewFraction.value = value;
widget.onScrubStart?.call();
}
: null,
onChanged: enabled
? (value) => setState(() => _previewFraction = value)
? (value) => _previewFraction.value = value
: null,
onChangeEnd: enabled
? (value) => unawaited(_finish(value, video.duration))