- r - 以节省内存的方式增长 data.frame
- ruby-on-rails - ruby/ruby on rails 内存泄漏检测
- android - 无法解析导入android.support.v7.app
- UNIX 域套接字与共享内存(映射文件)
在下面实现的代码中,我可以在页面底部显示带有 Fade
动画的对话框,现在,我想将 SlideTransition
添加到 ModalRoute
这个实现从底部滑动对话框,但我不能那样做
例如,我想要的是:
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
void main() => runApp(MyApp());
class MyApp extends StatelessWidget {
// This widget is the root of your application.
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Demo',
theme: ThemeData(
primarySwatch: Colors.blue,
),
home: MyHomePage(title: 'Flutter Demo Home Page'),
);
}
}
class MyHomePage extends StatefulWidget {
MyHomePage({Key key, this.title}) : super(key: key);
final String title;
@override
_MyHomePageState createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
int _counter = 0;
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text(widget.title),
),
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
Text(
'Open the popup window',
),
Text(
'$_counter',
style: Theme.of(context).textTheme.display1,
),
],
),
),
floatingActionButton: FloatingActionButton(
onPressed: () {
showPopup(context, _popupBody(), 'Popup Demo');
},
tooltip: 'Open Popup',
child: Icon(Icons.add),
), // This trailing comma makes auto-formatting nicer for build methods.
);
}
showPopup(BuildContext context, Widget widget, String title, {BuildContext popupContext}) {
Navigator.push(
context,
PopupLayout(
top: MediaQuery.of(context).size.height * 0.300,
left: 0,
right: 0,
bottom: 0,
child: PopupContent(
content: Scaffold(
body: widget,
),
),
),
);
}
Widget _popupBody() {
return Container(
child: Text('This is a popup window'),
);
}
}
class PopupLayout extends ModalRoute {
double top;
double bottom;
double left;
double right;
Color bgColor;
final Widget child;
@override
Duration get transitionDuration => Duration(milliseconds: 200);
@override
bool get opaque => false;
@override
bool get barrierDismissible => false;
@override
Color get barrierColor => bgColor == null ? Colors.black.withOpacity(0.5) : bgColor;
@override
String get barrierLabel => null;
@override
bool get maintainState => false;
PopupLayout({Key key, this.bgColor, @required this.child, this.top, this.bottom, this.left, this.right});
@override
Widget buildPage(
BuildContext context,
Animation<double> animation,
Animation<double> secondaryAnimation,
) {
if (top == null) this.top = 10;
if (bottom == null) this.bottom = 20;
if (left == null) this.left = 20;
if (right == null) this.right = 20;
return GestureDetector(
onTap: () {
// call this method here to hide soft keyboard
SystemChannels.textInput.invokeMethod('TextInput.hide');
},
child: Material(
// This makes sure that text and other content follows the material style
type: MaterialType.transparency,
//type: MaterialType.canvas,
// make sure that the overlay content is not cut off
child: SafeArea(
bottom: true,
child: _buildOverlayContent(context),
),
),
);
}
Widget _buildOverlayContent(BuildContext context) {
return Container(
margin: EdgeInsets.only(bottom: this.bottom, left: this.left, right: this.right, top: this.top),
child: SlideTransition(child: child),
);
}
@override
Widget buildTransitions(BuildContext context, Animation<double> animation, Animation<double> secondaryAnimation, Widget child) {
return FadeTransition(opacity: animation, child: child);
}
}
class PopupContent extends StatefulWidget {
final Widget content;
PopupContent({
Key key,
this.content,
}) : super(key: key);
_PopupContentState createState() => _PopupContentState();
}
class _PopupContentState extends State<PopupContent> {
@override
void initState() {
super.initState();
}
@override
Widget build(BuildContext context) {
return Container(
child: widget.content,
);
}
}
最佳答案
这是一个工作示例
import 'package:flutter/material.dart';
void main() => runApp(MyApp());
class MyApp extends StatelessWidget {
// This widget is the root of your application.
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Demo',
theme: ThemeData(
primarySwatch: Colors.blue,
),
home: MyHomePage(title: 'Flutter Demo Home Page'),
);
}
}
class MyHomePage extends StatefulWidget {
MyHomePage({Key key, this.title}) : super(key: key);
final String title;
@override
_MyHomePageState createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage>
with TickerProviderStateMixin {
void showPopup() {
AnimationController controller = AnimationController(
duration: const Duration(milliseconds: 400), vsync: this);
showDialog(
context: context,
builder: (_) => PopUp(
controller: controller,
),
);
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text(widget.title),
),
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
Text(
'You have pushed the button this many times:',
),
],
),
),
floatingActionButton: FloatingActionButton(
onPressed: showPopup,
tooltip: 'Increment',
child: Icon(Icons.add),
), // This trailing comma makes auto-formatting nicer for build methods.
);
}
}
class PopUp extends StatefulWidget {
final AnimationController controller;
PopUp({this.controller});
@override
State<StatefulWidget> createState() => PopUpState();
}
class PopUpState extends State<PopUp> {
Animation<double> opacityAnimation;
Tween<double> opacityTween = Tween<double>(begin: 0.0, end: 1.0);
Tween<double> marginTopTween = Tween<double>(begin: 600, end: 200);
Animation<double> marginTopAnimation;
AnimationStatus animationStatus;
@override
void initState() {
super.initState();
marginTopAnimation = marginTopTween.animate(widget.controller)
..addListener(() {
animationStatus = widget.controller.status;
if (animationStatus == AnimationStatus.dismissed) {
Navigator.of(context).pop();
}
if(this.mounted) {
setState(() {
});
}
});
widget.controller.forward();
}
@override
Widget build(BuildContext context) {
return FadeTransition(
opacity: opacityTween.animate(widget.controller),
child: GestureDetector(
onTap: () {
widget.controller.reverse();
},
child: Material(
color: Colors.transparent,
child: Container(
margin: EdgeInsets.only(
top: marginTopAnimation.value,
),
color: Colors.red,
child: Text("Container"),
),
),
),
);
}
@override
void dispose() {
widget.controller.dispose();
super.dispose();
}
}
更新 1:添加了 Material
作为 Container
的子项以修复 barrier not dismissing 错误。
更新 2:进行了一些更改,在障碍物消失时反转动画。
注意:屏幕截图未反射(reflect)更新的更改。这是原始答案的演示。
关于Flutter 添加自定义 SlideTransition 到 ModalRoute,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/57035483/
为了在 flutter 中获得类似模态的效果(当页面被推到当前页面的顶部时,背景为黑色并且足够透明,以便您可以在背景中看到后面的页面)。 我正在使用 ModalRoute 类在我当前页面的顶部显示一个
每次我调用 modalroute 以从命名路由中检索参数时,我都会得到 null。 这是代码片段: Navigator.pushNamed( context,
我用 flutter 编写了一个应用程序。我想更改字符串变量的状态。在我设置字符串变量的状态后,ModalRoute PopUpMenu 不显示更改的变量。如果我关闭 ModalRoute PopUp
在下面实现的代码中,我可以在页面底部显示带有 Fade 动画的对话框,现在,我想将 SlideTransition 添加到 ModalRoute这个实现从底部滑动对话框,但我不能那样做 例如,我想要的
当我将我的应用程序打开到登录屏幕时,屏幕工作正常但没有发生任何事情,现在,当我单击注册按钮并尝试单击返回登录时,出现此错误 ======== Exception caught by widge
我对 flutter 感到困惑,当我想从 statefulwidget (initstate) 读取参数并将其访问到小部件构建中时,该变量仍然为空。如何正确阅读?我的代码如下: import 'pac
在任何给定情况下是否有任何理由使用一个而不是另一个?我试图弄清楚为什么有两种方法可以做到这一点。我指的是“带参数导航”食谱食谱: https://flutter.dev/docs/cookbook/n
最近我正在迁移到空安全。更新了 firebase_analytics:^8.0.2。 现在面临 this.observer.subscribe(this, ModalRoute.of(context)
在我的应用程序中单击一个按钮会打开一个弹出窗口。单击该按钮一次,然后它工作正常,但是每当我连续单击该按钮 2 3 次时,就会出现下面给出的错误。 我收到此错误。 flutter: ══════════
我正在使用 Getx 状态管理。我有一个登录屏幕及其 GetxController。在那个 GetxController 中,我定义了一个像这样的 FormKey final formKey = Gl
我是一名优秀的程序员,十分优秀!