【发布时间】:2019-06-01 03:56:11
【问题描述】:
Flutter 中是否有一个内置的小部件可以在中间创建一个带有文本的分隔线?关于如何做的任何指南?像这样:(水平线中间的“OR”文本)
【问题讨论】:
标签: user-interface dart flutter material-design
Flutter 中是否有一个内置的小部件可以在中间创建一个带有文本的分隔线?关于如何做的任何指南?像这样:(水平线中间的“OR”文本)
【问题讨论】:
标签: user-interface dart flutter material-design
我已经对它进行了一些美化,代码是这样的
Row(
mainAxisAlignment: MainAxisAlignment.center,
children: const [
Expanded(
child: Divider(
indent: 20.0,
endIndent: 10.0,
thickness: 1,
),
),
Text(
"OR",
style: TextStyle(color: Colors.blueGrey),
),
Expanded(
child: Divider(
indent: 10.0,
endIndent: 20.0,
thickness: 1,
),
),
],
),
【讨论】:
没有颤振小部件可以做到这一点,我为自己创建的。 你可以这样做
import 'package:flutter/material.dart';
import 'package:flutter/widgets.dart';
class HorizontalOrLine extends StatelessWidget {
const HorizontalOrLine({
this.label,
this.height,
});
final String label;
final double height;
@override
Widget build(BuildContext context) {
return Row(children: <Widget>[
Expanded(
child: new Container(
margin: const EdgeInsets.only(left: 10.0, right: 15.0),
child: Divider(
color: Colors.black,
height: height,
)),
),
Text(label),
Expanded(
child: new Container(
margin: const EdgeInsets.only(left: 15.0, right: 10.0),
child: Divider(
color: Colors.black,
height: height,
)),
),
]);
}
}
用法如下:
HorizontalOrLine(height: 10,label: "OR")
【讨论】:
您可以简单地使用容器来实现:
new Container(height: 40, width: 1, color: Colors.grey,
margin: const EdgeInsets.only(left: 10.0, right: 10.0),),
如果你想要一条垂直线,改变它的高度并用宽度控制你的线的“粗细”。
如果要绘制水平线,请在宽度/高度之间反转这些逻辑。
在一行中使用它,您的文本位于两个容器的中间。
【讨论】:
import 'package:flutter/material.dart';
class HorizontalLineTitle extends StatelessWidget {
final String title;
final Color color;
final double lineHeight;
final double lineWidth;
final double paddingTop;
final double paddingBottom;
HorizontalLineTitle({
@required this.title,
@required this.color,
this.lineHeight,
this.lineWidth,
this.paddingTop,
this.paddingBottom,
});
Widget _line() {
return LayoutBuilder(
builder: (BuildContext context, BoxConstraints constraints) {
final boxWidth = constraints.constrainWidth();
final dashWidth = lineWidth ?? 10.0;
final dashHeight = lineHeight ?? 1.0;
final dashCount = (boxWidth / (2 * dashWidth)).floor();
return Flex(
children: List.generate(dashCount, (_) {
return SizedBox(
width: dashWidth,
height: dashHeight,
child: DecoratedBox(
decoration: BoxDecoration(color: color),
),
);
}),
mainAxisAlignment: MainAxisAlignment.spaceBetween,
direction: Axis.horizontal,
);
},
);
}
@override
Widget build(BuildContext context) {
var widgets = <Widget>[];
widgets.add(Expanded(child: _line()));
if (title != null && title != '') {
widgets.add(Padding(
padding: EdgeInsets.fromLTRB(10, 0, 10, 0),
child: Text(
title,
style: Theme.of(context).textTheme.title,
),
));
} else {
widgets.add(Container(width: 2.0));
}
widgets.add(Expanded(child: _line()));
return Padding(
padding: EdgeInsets.fromLTRB(
0.0, paddingTop ?? 0.0, 0.0, paddingBottom ?? 0.0),
child: Row(
children: widgets,
),
);
}
}
此小部件可用于拥有您需要的相同东西,但带有虚线。只是想发布此内容,以便人们可以使用它来根据自己的需要对其进行自定义。
【讨论】:
最好的办法是制作一个CustomPainter并画一条线
自定义画家:
class Drawhorizontalline extends CustomPainter {
Paint _paint;
bool reverse;
Drawhorizontalline(this.reverse) {
_paint = Paint()
..color = PPColors.tertiaryColor
..strokeWidth = 1
..strokeCap = StrokeCap.round;
}
@override
void paint(Canvas canvas, Size size) {
if (reverse) {
canvas.drawLine(Offset(-250.0, 0.0), Offset(-10.0, 0.0), _paint);
} else {
canvas.drawLine(Offset(10.0, 0.0), Offset(250.0, 0.0), _paint);
}
}
@override
bool shouldRepaint(CustomPainter oldDelegate) {
return false;
}
}
使用这个 CustomPainter
Widget getSeparateDivider() {
return Row(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
CustomPaint(painter: Drawhorizontalline(true)),
Text(
"OR",
style: TextStyle(
color: PPColors.primaryColor,
fontWeight: FontWeight.bold,
fontSize: PPUIHelper.FontSizeLarge),
),
CustomPaint(painter: Drawhorizontalline(false))
],
);
}
【讨论】:
扩展 Jerome 的答案 - 这是一个示例,展示了如何将其与其他内容一起嵌入,并且还有额外的边缘插入以更接近您想要的实际图片:
Column(children: <Widget>[
Row(
children: <Widget>[Text("above")],
),
Row(children: <Widget>[
Expanded(
child: new Container(
margin: const EdgeInsets.only(left: 10.0, right: 20.0),
child: Divider(
color: Colors.black,
height: 36,
)),
),
Text("OR"),
Expanded(
child: new Container(
margin: const EdgeInsets.only(left: 20.0, right: 10.0),
child: Divider(
color: Colors.black,
height: 36,
)),
),
]),
Row(
children: <Widget>[Text("below ")],
),
])
【讨论】:
您可以尝试使用Row 小部件。
Row(
children: <Widget>[
Expanded(
child: Divider()
),
Text("OR"),
Expanded(
child: Divider()
),
]
)
【讨论】:
Divider 具有的所有可选参数传递到自包含小部件中时,是否有某种方法可以将其移动到可重复使用的小部件中?你是否在保持可选参数的同时传递可选参数?