double.INFINITY là một khái niệm quan trọng trong Flutter, được sử dụng để xác định kích thước tối đa không giới hạn cho các widget. Hiểu và áp dụng đúng double.INFINITY sẽ giúp bạn tạo ra layout linh hoạt, responsive và tối ưu hiệu suất cho ứng dụng của mình. Bài viết này sẽ hướng dẫn chi tiết các trường hợp sử dụng phổ biến cùng với các best practices khi làm việc với double.INFINITY.
HƯỚNG DẪN SỬ DỤNG double.INFINITY TRONG FLUTTER
1. Khái niệm double.INFINITY
double.INFINITY là một giá trị đặc biệt trong Dart/Flutter đại diện cho vô cùng. Nó lớn hơn bất kỳ số hữu hạn nào.
void main() {
print(double.INFINITY > 999999999); // true
print(double.INFINITY == double.INFINITY); // true
print(double.INFINITY + 1 == double.INFINITY); // true
}
2. Sử dụng trong Widget Sizing
a. Container và SizedBox
Container(
width: double.infinity, // Chiều rộng tối đa có thể
height: 100,
color: Colors.blue,
child: Text('Full width container'),
)
b. Trong ListView và Column
ListView(
children: [
Container(
constraints: BoxConstraints(
maxWidth: double.infinity,
minHeight: 50,
),
color: Colors.red,
),
],
)
3. Sử dụng trong Constraints
a. Flexible Constraints
ConstrainedBox(
constraints: BoxConstraints(
maxWidth: double.infinity,
maxHeight: double.infinity,
),
child: Container(
color: Colors.green,
),
)
b. CustomScrollView và SliverFillRemaining
CustomScrollView(
slivers: [
SliverFillRemaining(
hasScrollBody: false,
child: Container(
constraints: BoxConstraints.expand(
width: double.infinity,
height: double.infinity,
),
),
),
],
)
4. Trường hợp nên sử dụng
a. Responsive Design
class ResponsiveWidget extends StatelessWidget {
@override
Widget build(BuildContext context) {
return LayoutBuilder(
builder: (context, constraints) {
return Container(
width: constraints.maxWidth == double.infinity
? MediaQuery.of(context).size.width
: constraints.maxWidth,
child: Text('Responsive content'),
);
},
);
}
}
b. Wrap Content
Wrap(
children: [
Container(
constraints: BoxConstraints(
maxWidth: double.infinity,
),
child: Text('This text can wrap to multiple lines if needed'),
),
],
)
5. Tối ưu hiệu suất
a. Tránh lạm dụng
// KHÔNG NÊN
Container(
width: double.infinity,
height: double.infinity,
child: SingleChildScrollView(
child: Column(
children: List.generate(1000, (index) => Container()),
),
),
)
// NÊN
LayoutBuilder(
builder: (context, constraints) {
return Container(
width: constraints.maxWidth,
height: constraints.maxHeight,
child: ListView.builder(
itemCount: 1000,
itemBuilder: (context, index) => Container(),
),
);
},
)
6. Các trường hợp đặc biệt
a. AnimatedContainer
AnimatedContainer(
duration: Duration(milliseconds: 300),
width: isExpanded ? double.infinity : 200,
height: 100,
color: Colors.blue,
)
b. MediaQuery
class ResponsiveScreen extends StatelessWidget {
@override
Widget build(BuildContext context) {
final screenWidth = MediaQuery.of(context).size.width;
return Container(
width: screenWidth == double.infinity
? 600
: screenWidth * 0.9,
child: Card(
child: Text('Responsive card'),
),
);
}
}
7. Debug và xử lý lỗi
void debugConstraints(BoxConstraints constraints) {
if (constraints.maxWidth == double.infinity &&
constraints.maxHeight == double.infinity) {
print('Warning: Unbounded constraints detected');
}
}
class DebugContainer extends StatelessWidget {
@override
Widget build(BuildContext context) {
return LayoutBuilder(
builder: (context, constraints) {
debugConstraints(constraints);
return Container();
},
);
}
}