mirror of
https://github.com/flutter/flutter.git
synced 2026-02-20 02:29:02 +08:00
Move HeroController into heroes.dart and PageRoute into pages.dart
This commit is contained in:
parent
519b190c0f
commit
fa31a4ad37
@ -1,122 +0,0 @@
|
||||
// Copyright 2015 The Chromium Authors. All rights reserved.
|
||||
// Use of this source code is governed by a BSD-style license that can be
|
||||
// found in the LICENSE file.
|
||||
|
||||
import 'package:flutter/animation.dart';
|
||||
import 'package:flutter/rendering.dart';
|
||||
import 'package:flutter/scheduler.dart';
|
||||
|
||||
import 'basic.dart';
|
||||
import 'framework.dart';
|
||||
import 'heroes.dart';
|
||||
import 'navigator.dart';
|
||||
import 'overlay.dart';
|
||||
import 'routes.dart';
|
||||
|
||||
class HeroController extends NavigatorObserver {
|
||||
HeroController() {
|
||||
_party = new HeroParty(onQuestFinished: _handleQuestFinished);
|
||||
}
|
||||
|
||||
HeroParty _party;
|
||||
PerformanceView _performance;
|
||||
ModalRoute _from;
|
||||
ModalRoute _to;
|
||||
|
||||
final List<OverlayEntry> _overlayEntries = new List<OverlayEntry>();
|
||||
|
||||
void didPush(Route route, Route previousRoute) {
|
||||
assert(navigator != null);
|
||||
assert(route != null);
|
||||
if (route is PageRoute) {
|
||||
assert(route.performance != null);
|
||||
if (previousRoute is PageRoute) // could be null
|
||||
_from = previousRoute;
|
||||
_to = route;
|
||||
_performance = route.performance;
|
||||
_checkForHeroQuest();
|
||||
}
|
||||
}
|
||||
|
||||
void didPop(Route route, Route previousRoute) {
|
||||
assert(navigator != null);
|
||||
assert(route != null);
|
||||
if (route is PageRoute) {
|
||||
assert(route.performance != null);
|
||||
if (previousRoute is PageRoute) {
|
||||
_to = previousRoute;
|
||||
_from = route;
|
||||
_performance = route.performance;
|
||||
_checkForHeroQuest();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void _checkForHeroQuest() {
|
||||
if (_from != null && _to != null && _from != _to) {
|
||||
_to.offstage = _to.performance.status != PerformanceStatus.completed;
|
||||
scheduler.addPostFrameCallback(_updateQuest);
|
||||
}
|
||||
}
|
||||
|
||||
void _handleQuestFinished() {
|
||||
_removeHeroesFromOverlay();
|
||||
_from = null;
|
||||
_to = null;
|
||||
_performance = null;
|
||||
}
|
||||
|
||||
Rect _getAnimationArea(BuildContext context) {
|
||||
RenderBox box = context.findRenderObject();
|
||||
Point topLeft = box.localToGlobal(Point.origin);
|
||||
Point bottomRight = box.localToGlobal(box.size.bottomRight(Point.origin));
|
||||
return new Rect.fromLTRB(topLeft.x, topLeft.y, bottomRight.x, bottomRight.y);
|
||||
}
|
||||
|
||||
void _removeHeroesFromOverlay() {
|
||||
for (OverlayEntry entry in _overlayEntries)
|
||||
entry.remove();
|
||||
_overlayEntries.clear();
|
||||
}
|
||||
|
||||
void _addHeroesToOverlay(Iterable<Widget> heroes, OverlayState overlay) {
|
||||
for (Widget hero in heroes) {
|
||||
OverlayEntry entry = new OverlayEntry(builder: (_) => hero);
|
||||
overlay.insert(entry);
|
||||
_overlayEntries.add(entry);
|
||||
}
|
||||
}
|
||||
|
||||
Set<Key> _getMostValuableKeys() {
|
||||
assert(_from != null);
|
||||
assert(_to != null);
|
||||
Set<Key> result = new Set<Key>();
|
||||
if (_from.settings.mostValuableKeys != null)
|
||||
result.addAll(_from.settings.mostValuableKeys);
|
||||
if (_to.settings.mostValuableKeys != null)
|
||||
result.addAll(_to.settings.mostValuableKeys);
|
||||
return result;
|
||||
}
|
||||
|
||||
void _updateQuest(Duration timeStamp) {
|
||||
Set<Key> mostValuableKeys = _getMostValuableKeys();
|
||||
|
||||
Map<Object, HeroHandle> heroesFrom = _party.isEmpty ?
|
||||
Hero.of(_from.subtreeContext, mostValuableKeys) : _party.getHeroesToAnimate();
|
||||
|
||||
Map<Object, HeroHandle> heroesTo = Hero.of(_to.subtreeContext, mostValuableKeys);
|
||||
_to.offstage = false;
|
||||
|
||||
PerformanceView performance = _performance;
|
||||
Curve curve = Curves.ease;
|
||||
if (performance.status == PerformanceStatus.reverse) {
|
||||
performance = new ReversePerformance(performance);
|
||||
curve = new Interval(performance.progress, 1.0, curve: curve);
|
||||
}
|
||||
|
||||
_party.animate(heroesFrom, heroesTo, _getAnimationArea(navigator.context), curve);
|
||||
_removeHeroesFromOverlay();
|
||||
Iterable<Widget> heroes = _party.getWidgets(navigator.context, performance);
|
||||
_addHeroesToOverlay(heroes, navigator.overlay);
|
||||
}
|
||||
}
|
||||
@ -4,9 +4,14 @@
|
||||
|
||||
import 'package:flutter/animation.dart';
|
||||
import 'package:flutter/rendering.dart';
|
||||
import 'package:flutter/scheduler.dart';
|
||||
|
||||
import 'basic.dart';
|
||||
import 'framework.dart';
|
||||
import 'navigator.dart';
|
||||
import 'overlay.dart';
|
||||
import 'pages.dart';
|
||||
import 'routes.dart';
|
||||
import 'transitions.dart';
|
||||
|
||||
// Heroes are the parts of an application's screen-to-screen transitions where a
|
||||
@ -412,3 +417,111 @@ class HeroParty {
|
||||
|
||||
String toString() => '$_heroes';
|
||||
}
|
||||
|
||||
class HeroController extends NavigatorObserver {
|
||||
HeroController() {
|
||||
_party = new HeroParty(onQuestFinished: _handleQuestFinished);
|
||||
}
|
||||
|
||||
HeroParty _party;
|
||||
PerformanceView _performance;
|
||||
ModalRoute _from;
|
||||
ModalRoute _to;
|
||||
|
||||
final List<OverlayEntry> _overlayEntries = new List<OverlayEntry>();
|
||||
|
||||
void didPush(Route route, Route previousRoute) {
|
||||
assert(navigator != null);
|
||||
assert(route != null);
|
||||
if (route is PageRoute) {
|
||||
assert(route.performance != null);
|
||||
if (previousRoute is PageRoute) // could be null
|
||||
_from = previousRoute;
|
||||
_to = route;
|
||||
_performance = route.performance;
|
||||
_checkForHeroQuest();
|
||||
}
|
||||
}
|
||||
|
||||
void didPop(Route route, Route previousRoute) {
|
||||
assert(navigator != null);
|
||||
assert(route != null);
|
||||
if (route is PageRoute) {
|
||||
assert(route.performance != null);
|
||||
if (previousRoute is PageRoute) {
|
||||
_to = previousRoute;
|
||||
_from = route;
|
||||
_performance = route.performance;
|
||||
_checkForHeroQuest();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void _checkForHeroQuest() {
|
||||
if (_from != null && _to != null && _from != _to) {
|
||||
_to.offstage = _to.performance.status != PerformanceStatus.completed;
|
||||
scheduler.addPostFrameCallback(_updateQuest);
|
||||
}
|
||||
}
|
||||
|
||||
void _handleQuestFinished() {
|
||||
_removeHeroesFromOverlay();
|
||||
_from = null;
|
||||
_to = null;
|
||||
_performance = null;
|
||||
}
|
||||
|
||||
Rect _getAnimationArea(BuildContext context) {
|
||||
RenderBox box = context.findRenderObject();
|
||||
Point topLeft = box.localToGlobal(Point.origin);
|
||||
Point bottomRight = box.localToGlobal(box.size.bottomRight(Point.origin));
|
||||
return new Rect.fromLTRB(topLeft.x, topLeft.y, bottomRight.x, bottomRight.y);
|
||||
}
|
||||
|
||||
void _removeHeroesFromOverlay() {
|
||||
for (OverlayEntry entry in _overlayEntries)
|
||||
entry.remove();
|
||||
_overlayEntries.clear();
|
||||
}
|
||||
|
||||
void _addHeroesToOverlay(Iterable<Widget> heroes, OverlayState overlay) {
|
||||
for (Widget hero in heroes) {
|
||||
OverlayEntry entry = new OverlayEntry(builder: (_) => hero);
|
||||
overlay.insert(entry);
|
||||
_overlayEntries.add(entry);
|
||||
}
|
||||
}
|
||||
|
||||
Set<Key> _getMostValuableKeys() {
|
||||
assert(_from != null);
|
||||
assert(_to != null);
|
||||
Set<Key> result = new Set<Key>();
|
||||
if (_from.settings.mostValuableKeys != null)
|
||||
result.addAll(_from.settings.mostValuableKeys);
|
||||
if (_to.settings.mostValuableKeys != null)
|
||||
result.addAll(_to.settings.mostValuableKeys);
|
||||
return result;
|
||||
}
|
||||
|
||||
void _updateQuest(Duration timeStamp) {
|
||||
Set<Key> mostValuableKeys = _getMostValuableKeys();
|
||||
|
||||
Map<Object, HeroHandle> heroesFrom = _party.isEmpty ?
|
||||
Hero.of(_from.subtreeContext, mostValuableKeys) : _party.getHeroesToAnimate();
|
||||
|
||||
Map<Object, HeroHandle> heroesTo = Hero.of(_to.subtreeContext, mostValuableKeys);
|
||||
_to.offstage = false;
|
||||
|
||||
PerformanceView performance = _performance;
|
||||
Curve curve = Curves.ease;
|
||||
if (performance.status == PerformanceStatus.reverse) {
|
||||
performance = new ReversePerformance(performance);
|
||||
curve = new Interval(performance.progress, 1.0, curve: curve);
|
||||
}
|
||||
|
||||
_party.animate(heroesFrom, heroesTo, _getAnimationArea(navigator.context), curve);
|
||||
_removeHeroesFromOverlay();
|
||||
Iterable<Widget> heroes = _party.getWidgets(navigator.context, performance);
|
||||
_addHeroesToOverlay(heroes, navigator.overlay);
|
||||
}
|
||||
}
|
||||
|
||||
22
packages/flutter/lib/src/widgets/pages.dart
Normal file
22
packages/flutter/lib/src/widgets/pages.dart
Normal file
@ -0,0 +1,22 @@
|
||||
// Copyright 2015 The Chromium Authors. All rights reserved.
|
||||
// Use of this source code is governed by a BSD-style license that can be
|
||||
// found in the LICENSE file.
|
||||
|
||||
import 'dart:async';
|
||||
|
||||
import 'heroes.dart';
|
||||
import 'navigator.dart';
|
||||
import 'overlay.dart';
|
||||
import 'routes.dart';
|
||||
|
||||
/// A modal route that replaces the entire screen.
|
||||
abstract class PageRoute<T> extends ModalRoute<T> {
|
||||
PageRoute({
|
||||
Completer<T> completer,
|
||||
NamedRouteSettings settings: const NamedRouteSettings()
|
||||
}) : super(completer: completer, settings: settings);
|
||||
bool get opaque => true;
|
||||
bool get barrierDismissable => false;
|
||||
bool canTransitionTo(TransitionRoute nextRoute) => nextRoute is PageRoute;
|
||||
bool canTransitionFrom(TransitionRoute nextRoute) => nextRoute is PageRoute;
|
||||
}
|
||||
@ -13,6 +13,7 @@ import 'modal_barrier.dart';
|
||||
import 'navigator.dart';
|
||||
import 'overlay.dart';
|
||||
import 'page_storage.dart';
|
||||
import 'pages.dart';
|
||||
|
||||
const _kTransparent = const Color(0x00000000);
|
||||
|
||||
@ -458,15 +459,3 @@ abstract class PopupRoute<T> extends ModalRoute<T> {
|
||||
super.didPushNext(nextRoute);
|
||||
}
|
||||
}
|
||||
|
||||
/// A modal route that replaces the entire screen.
|
||||
abstract class PageRoute<T> extends ModalRoute<T> {
|
||||
PageRoute({
|
||||
Completer<T> completer,
|
||||
NamedRouteSettings settings: const NamedRouteSettings()
|
||||
}) : super(completer: completer, settings: settings);
|
||||
bool get opaque => true;
|
||||
bool get barrierDismissable => false;
|
||||
bool canTransitionTo(TransitionRoute nextRoute) => nextRoute is PageRoute;
|
||||
bool canTransitionFrom(TransitionRoute nextRoute) => nextRoute is PageRoute;
|
||||
}
|
||||
|
||||
@ -17,7 +17,6 @@ export 'src/widgets/focus.dart';
|
||||
export 'src/widgets/framework.dart';
|
||||
export 'src/widgets/gesture_detector.dart';
|
||||
export 'src/widgets/gridpaper.dart';
|
||||
export 'src/widgets/hero_controller.dart';
|
||||
export 'src/widgets/heroes.dart';
|
||||
export 'src/widgets/homogeneous_viewport.dart';
|
||||
export 'src/widgets/media_query.dart';
|
||||
@ -28,6 +27,7 @@ export 'src/widgets/navigator.dart';
|
||||
export 'src/widgets/notification_listener.dart';
|
||||
export 'src/widgets/overlay.dart';
|
||||
export 'src/widgets/page_storage.dart';
|
||||
export 'src/widgets/pages.dart';
|
||||
export 'src/widgets/placeholder.dart';
|
||||
export 'src/widgets/routes.dart';
|
||||
export 'src/widgets/scrollable.dart';
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user