mirror of
https://github.com/Myzel394/quid_faciam_hodie.git
synced 2025-06-21 00:20:29 +02:00
added overlay disappear after a short time
This commit is contained in:
parent
f5fd31d592
commit
2339fd27a0
15
lib/models/timeline_overlay.dart
Normal file
15
lib/models/timeline_overlay.dart
Normal file
@ -0,0 +1,15 @@
|
|||||||
|
import 'package:flutter/material.dart';
|
||||||
|
|
||||||
|
class TimelineOverlay extends ChangeNotifier {
|
||||||
|
bool _showOverlay = true;
|
||||||
|
|
||||||
|
bool get showOverlay => _showOverlay;
|
||||||
|
|
||||||
|
void hideOverlay() => setShowOverlay(false);
|
||||||
|
void restoreOverlay() => setShowOverlay(true);
|
||||||
|
|
||||||
|
void setShowOverlay(bool showOverlay) {
|
||||||
|
_showOverlay = showOverlay;
|
||||||
|
notifyListeners();
|
||||||
|
}
|
||||||
|
}
|
@ -1,8 +1,10 @@
|
|||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
|
import 'package:provider/provider.dart';
|
||||||
import 'package:share_location/controllers/memory_slide_controller.dart';
|
import 'package:share_location/controllers/memory_slide_controller.dart';
|
||||||
import 'package:share_location/controllers/status_controller.dart';
|
import 'package:share_location/controllers/status_controller.dart';
|
||||||
import 'package:share_location/enums.dart';
|
import 'package:share_location/enums.dart';
|
||||||
import 'package:share_location/foreign_types/memory.dart';
|
import 'package:share_location/foreign_types/memory.dart';
|
||||||
|
import 'package:share_location/models/timeline_overlay.dart';
|
||||||
import 'package:share_location/widgets/status.dart';
|
import 'package:share_location/widgets/status.dart';
|
||||||
|
|
||||||
import 'memory.dart';
|
import 'memory.dart';
|
||||||
@ -66,35 +68,38 @@ class _MemorySlideState extends State<MemorySlide>
|
|||||||
|
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
return Status(
|
return Consumer<TimelineOverlay>(
|
||||||
controller: controller,
|
builder: (context, overlayController, _) => Status(
|
||||||
child: MemoryView(
|
controller: controller,
|
||||||
creationDate: widget.memory.creationDate,
|
disabled: !overlayController.showOverlay,
|
||||||
location: widget.memory.location,
|
child: MemoryView(
|
||||||
filename: widget.memory.filename,
|
creationDate: widget.memory.creationDate,
|
||||||
loopVideo: false,
|
location: widget.memory.location,
|
||||||
onFileDownloaded: () {
|
filename: widget.memory.filename,
|
||||||
if (widget.memory.type == MemoryType.photo) {
|
loopVideo: false,
|
||||||
initializeAnimation(DEFAULT_IMAGE_DURATION);
|
onFileDownloaded: () {
|
||||||
}
|
if (widget.memory.type == MemoryType.photo) {
|
||||||
},
|
initializeAnimation(DEFAULT_IMAGE_DURATION);
|
||||||
onVideoControllerInitialized: (controller) {
|
}
|
||||||
if (mounted) {
|
},
|
||||||
initializeAnimation(controller.value.duration);
|
onVideoControllerInitialized: (controller) {
|
||||||
|
if (mounted) {
|
||||||
|
initializeAnimation(controller.value.duration);
|
||||||
|
|
||||||
widget.controller.addListener(() {
|
widget.controller.addListener(() {
|
||||||
if (!mounted) {
|
if (!mounted) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (widget.controller.paused) {
|
if (widget.controller.paused) {
|
||||||
controller.pause();
|
controller.pause();
|
||||||
} else {
|
} else {
|
||||||
controller.play();
|
controller.play();
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
),
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -7,10 +7,12 @@ const BAR_HEIGHT = 4.0;
|
|||||||
class Status extends StatefulWidget {
|
class Status extends StatefulWidget {
|
||||||
final StatusController? controller;
|
final StatusController? controller;
|
||||||
final Widget child;
|
final Widget child;
|
||||||
|
final bool disabled;
|
||||||
|
|
||||||
const Status({
|
const Status({
|
||||||
Key? key,
|
Key? key,
|
||||||
required this.child,
|
required this.child,
|
||||||
|
this.disabled = false,
|
||||||
this.controller,
|
this.controller,
|
||||||
}) : super(key: key);
|
}) : super(key: key);
|
||||||
|
|
||||||
@ -29,6 +31,12 @@ class _StatusState extends State<Status> with TickerProviderStateMixin {
|
|||||||
if (widget.controller != null && animationController == null) {
|
if (widget.controller != null && animationController == null) {
|
||||||
initializeAnimation();
|
initializeAnimation();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (widget.disabled) {
|
||||||
|
animationController?.stop();
|
||||||
|
} else {
|
||||||
|
animationController?.forward();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@override
|
@override
|
||||||
@ -75,28 +83,33 @@ class _StatusState extends State<Status> with TickerProviderStateMixin {
|
|||||||
height: BAR_HEIGHT,
|
height: BAR_HEIGHT,
|
||||||
child: Padding(
|
child: Padding(
|
||||||
padding: const EdgeInsets.symmetric(horizontal: SMALL_SPACE),
|
padding: const EdgeInsets.symmetric(horizontal: SMALL_SPACE),
|
||||||
child: (widget.controller == null)
|
child: AnimatedOpacity(
|
||||||
? ClipRRect(
|
duration: const Duration(milliseconds: 500),
|
||||||
borderRadius: BorderRadius.circular(HUGE_SPACE),
|
curve: Curves.linearToEaseOut,
|
||||||
child: LinearProgressIndicator(
|
opacity: widget.disabled ? 0.0 : 1.0,
|
||||||
value: null,
|
child: (widget.controller == null)
|
||||||
valueColor: AlwaysStoppedAnimation<Color>(
|
? ClipRRect(
|
||||||
Colors.white.withOpacity(.3)),
|
|
||||||
backgroundColor: Colors.white.withOpacity(0.1),
|
|
||||||
),
|
|
||||||
)
|
|
||||||
: AnimatedBuilder(
|
|
||||||
animation: animation,
|
|
||||||
builder: (_, __) => ClipRRect(
|
|
||||||
borderRadius: BorderRadius.circular(HUGE_SPACE),
|
borderRadius: BorderRadius.circular(HUGE_SPACE),
|
||||||
child: LinearProgressIndicator(
|
child: LinearProgressIndicator(
|
||||||
value: animation.value,
|
value: null,
|
||||||
valueColor:
|
valueColor: AlwaysStoppedAnimation<Color>(
|
||||||
const AlwaysStoppedAnimation<Color>(Colors.white),
|
Colors.white.withOpacity(.3)),
|
||||||
backgroundColor: Colors.white.withOpacity(0.1),
|
backgroundColor: Colors.white.withOpacity(0.1),
|
||||||
),
|
),
|
||||||
|
)
|
||||||
|
: AnimatedBuilder(
|
||||||
|
animation: animation,
|
||||||
|
builder: (_, __) => ClipRRect(
|
||||||
|
borderRadius: BorderRadius.circular(HUGE_SPACE),
|
||||||
|
child: LinearProgressIndicator(
|
||||||
|
value: animation.value,
|
||||||
|
valueColor:
|
||||||
|
const AlwaysStoppedAnimation<Color>(Colors.white),
|
||||||
|
backgroundColor: Colors.white.withOpacity(0.1),
|
||||||
|
),
|
||||||
|
),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
],
|
],
|
||||||
|
@ -1,8 +1,12 @@
|
|||||||
|
import 'dart:async';
|
||||||
|
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:intl/intl.dart';
|
import 'package:intl/intl.dart';
|
||||||
|
import 'package:provider/provider.dart';
|
||||||
import 'package:share_location/constants/spacing.dart';
|
import 'package:share_location/constants/spacing.dart';
|
||||||
import 'package:share_location/controllers/memory_slide_controller.dart';
|
import 'package:share_location/controllers/memory_slide_controller.dart';
|
||||||
import 'package:share_location/foreign_types/memory.dart';
|
import 'package:share_location/foreign_types/memory.dart';
|
||||||
|
import 'package:share_location/models/timeline_overlay.dart';
|
||||||
import 'package:share_location/widgets/memory_slide.dart';
|
import 'package:share_location/widgets/memory_slide.dart';
|
||||||
|
|
||||||
class TimelinePage extends StatefulWidget {
|
class TimelinePage extends StatefulWidget {
|
||||||
@ -24,9 +28,12 @@ class TimelinePage extends StatefulWidget {
|
|||||||
}
|
}
|
||||||
|
|
||||||
class _TimelinePageState extends State<TimelinePage> {
|
class _TimelinePageState extends State<TimelinePage> {
|
||||||
|
final timelineOverlayController = TimelineOverlay();
|
||||||
final pageController = PageController();
|
final pageController = PageController();
|
||||||
late final MemorySlideController controller;
|
late final MemorySlideController controller;
|
||||||
|
|
||||||
|
Timer? overlayRemover;
|
||||||
|
|
||||||
@override
|
@override
|
||||||
void initState() {
|
void initState() {
|
||||||
super.initState();
|
super.initState();
|
||||||
@ -52,6 +59,7 @@ class _TimelinePageState extends State<TimelinePage> {
|
|||||||
@override
|
@override
|
||||||
void dispose() {
|
void dispose() {
|
||||||
controller.dispose();
|
controller.dispose();
|
||||||
|
timelineOverlayController.dispose();
|
||||||
|
|
||||||
super.dispose();
|
super.dispose();
|
||||||
}
|
}
|
||||||
@ -61,11 +69,23 @@ class _TimelinePageState extends State<TimelinePage> {
|
|||||||
return GestureDetector(
|
return GestureDetector(
|
||||||
onTapDown: (_) {
|
onTapDown: (_) {
|
||||||
controller.setPaused(true);
|
controller.setPaused(true);
|
||||||
|
|
||||||
|
overlayRemover = Timer(
|
||||||
|
const Duration(milliseconds: 200),
|
||||||
|
timelineOverlayController.hideOverlay,
|
||||||
|
);
|
||||||
},
|
},
|
||||||
onTapUp: (_) {
|
onTapUp: (_) {
|
||||||
|
overlayRemover?.cancel();
|
||||||
|
|
||||||
controller.setPaused(false);
|
controller.setPaused(false);
|
||||||
|
|
||||||
|
timelineOverlayController.restoreOverlay();
|
||||||
},
|
},
|
||||||
onTapCancel: () {
|
onTapCancel: () {
|
||||||
|
overlayRemover?.cancel();
|
||||||
|
|
||||||
|
timelineOverlayController.restoreOverlay();
|
||||||
controller.setPaused(false);
|
controller.setPaused(false);
|
||||||
},
|
},
|
||||||
onHorizontalDragEnd: (details) {
|
onHorizontalDragEnd: (details) {
|
||||||
@ -85,30 +105,43 @@ class _TimelinePageState extends State<TimelinePage> {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
child: Stack(
|
child: ChangeNotifierProvider<TimelineOverlay>(
|
||||||
fit: StackFit.expand,
|
create: (_) => timelineOverlayController,
|
||||||
children: <Widget>[
|
child: Stack(
|
||||||
PageView.builder(
|
fit: StackFit.expand,
|
||||||
controller: pageController,
|
children: <Widget>[
|
||||||
physics: const NeverScrollableScrollPhysics(),
|
PageView.builder(
|
||||||
scrollDirection: Axis.horizontal,
|
controller: pageController,
|
||||||
itemBuilder: (_, __) => MemorySlide(
|
physics: const NeverScrollableScrollPhysics(),
|
||||||
key: Key(controller.index.toString()),
|
scrollDirection: Axis.horizontal,
|
||||||
controller: controller,
|
itemBuilder: (_, __) => MemorySlide(
|
||||||
memory: widget.memories[controller.index],
|
key: Key(controller.index.toString()),
|
||||||
|
controller: controller,
|
||||||
|
memory: widget.memories[controller.index],
|
||||||
|
),
|
||||||
|
itemCount: widget.memories.length,
|
||||||
),
|
),
|
||||||
itemCount: widget.memories.length,
|
Padding(
|
||||||
),
|
padding: const EdgeInsets.only(
|
||||||
Padding(
|
top: LARGE_SPACE,
|
||||||
padding: const EdgeInsets.only(
|
left: MEDIUM_SPACE,
|
||||||
top: LARGE_SPACE, left: MEDIUM_SPACE, right: MEDIUM_SPACE),
|
right: MEDIUM_SPACE,
|
||||||
child: Text(
|
),
|
||||||
DateFormat('dd. MMMM yyyy').format(widget.date),
|
child: Consumer<TimelineOverlay>(
|
||||||
textAlign: TextAlign.center,
|
builder: (context, overlayController, _) => AnimatedOpacity(
|
||||||
style: Theme.of(context).textTheme.headline1,
|
duration: const Duration(milliseconds: 500),
|
||||||
|
curve: Curves.linearToEaseOut,
|
||||||
|
opacity: overlayController.showOverlay ? 1.0 : 0.0,
|
||||||
|
child: Text(
|
||||||
|
DateFormat('dd. MMMM yyyy').format(widget.date),
|
||||||
|
textAlign: TextAlign.center,
|
||||||
|
style: Theme.of(context).textTheme.headline1,
|
||||||
|
),
|
||||||
|
),
|
||||||
|
),
|
||||||
),
|
),
|
||||||
),
|
],
|
||||||
],
|
),
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
14
pubspec.lock
14
pubspec.lock
@ -310,6 +310,13 @@ packages:
|
|||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.0.2"
|
version: "1.0.2"
|
||||||
|
nested:
|
||||||
|
dependency: transitive
|
||||||
|
description:
|
||||||
|
name: nested
|
||||||
|
url: "https://pub.dartlang.org"
|
||||||
|
source: hosted
|
||||||
|
version: "1.0.0"
|
||||||
path:
|
path:
|
||||||
dependency: "direct main"
|
dependency: "direct main"
|
||||||
description:
|
description:
|
||||||
@ -457,6 +464,13 @@ packages:
|
|||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "0.3.0"
|
version: "0.3.0"
|
||||||
|
provider:
|
||||||
|
dependency: "direct main"
|
||||||
|
description:
|
||||||
|
name: provider
|
||||||
|
url: "https://pub.dartlang.org"
|
||||||
|
source: hosted
|
||||||
|
version: "6.0.3"
|
||||||
quiver:
|
quiver:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
|
@ -45,6 +45,7 @@ dependencies:
|
|||||||
intl: ^0.17.0
|
intl: ^0.17.0
|
||||||
property_change_notifier: ^0.3.0
|
property_change_notifier: ^0.3.0
|
||||||
path: ^1.8.1
|
path: ^1.8.1
|
||||||
|
provider: ^6.0.3
|
||||||
|
|
||||||
dev_dependencies:
|
dev_dependencies:
|
||||||
flutter_test:
|
flutter_test:
|
||||||
|
Loading…
x
Reference in New Issue
Block a user