VStack
A vertical stack layout component that arranges its children vertically with configurable spacing and alignment.
Overview
VStack provides vertical layout capabilities using a custom RenderBox implementation. It demonstrates how Flutter’s layout system works under the hood, including support for flexible children via VCustomFlexible and VCustomExpanded.
Primitives Used: Custom RenderBox, CustomMultiChildLayout, ParentDataWidget
Basic Usage
import 'package:primitive_ui/primitive_ui.dart';
VStack(
spacing: 16.0,
children: [
Text('Fixed Height'),
VCustomExpanded(
child: Container(color: Colors.blue),
),
Text('Fixed Height'),
],
)API Reference
Constructor
VStack({
Key? key,
required List<Widget> children,
double spacing = 0.0,
CrossAxisAlignment crossAxisAlignment = CrossAxisAlignment.start,
MainAxisAlignment mainAxisAlignment = MainAxisAlignment.start,
MainAxisSize mainAxisSize = MainAxisSize.max,
})Parameters
| Parameter | Type | Required | Default | Description |
|---|---|---|---|---|
children | List<Widget> | ✓ | — | The widgets to display in the vertical stack |
spacing | double | ✗ | 0.0 | Vertical spacing between children (must be >= 0) |
crossAxisAlignment | CrossAxisAlignment | ✗ | CrossAxisAlignment.start | How to align children horizontally |
mainAxisAlignment | MainAxisAlignment | ✗ | MainAxisAlignment.start | How to align children vertically |
mainAxisSize | MainAxisSize | ✗ | MainAxisSize.max | Whether to take maximum or minimum vertical space |
VCustomFlexible & VCustomExpanded
Wrap children in these widgets to control their flex behavior.
VCustomFlexible
VCustomFlexible({
Key? key,
int flex = 1,
FlexFit fit = FlexFit.loose,
required Widget child,
})VCustomExpanded
Shortcut for VCustomFlexible(fit: FlexFit.tight).
VCustomExpanded({
Key? key,
int flex = 1,
required Widget child,
})Examples
Different Alignments
Start
VStack(
crossAxisAlignment: CrossAxisAlignment.start,
spacing: 8.0,
children: [
Container(width: 100, height: 50, color: Colors.red),
Container(width: 150, height: 50, color: Colors.green),
Container(width: 80, height: 50, color: Colors.blue),
],
)Flexible Layouts
Expanded
// Fills available vertical space
VStack(
children: [
Container(height: 50, color: Colors.red),
VCustomExpanded(
child: Container(color: Colors.blue), // Takes remaining space
),
Container(height: 50, color: Colors.green),
],
)Implementation Details
Layout Algorithm
The VStack layout process has been upgraded to support two-pass layout for flex children:
-
Pass 1 (Fixed Children): Measure all non-flex children.
if (flex == 0) { child.layout(...); totalNonFlexHeight += child.size.height; } -
Calculate Free Space: Determine space available for flex children.
freeSpace = availableHeight - totalNonFlexHeight - totalSpacing; -
Pass 2 (Flex Children): Measure flex children using allocated space.
childHeight = (freeSpace * flex) / totalFlex; child.layout(constraints.tighten(height: childHeight)); -
Positioning: Place all children in sequence.
Parent Data
VStack uses _VStackParentData to store flex and fit properties for each child, populated by VCustomFlexible.
Limitations
Known Limitations:
- No built-in overflow handling (use
SingleChildScrollViewwhen needed) - No spacer or divider components built-in (use
VCustomExpandedwithSizedBoxorContainerfor spacer) - All children are measured even if not visible
Differences from Column
| Feature | VStack | Column |
|---|---|---|
| Flexible/Expanded | ✅ Supported (via VCustomFlexible) | ✅ Supported |
| Baseline alignment | ❌ Not supported | ✅ Supported |
| Text direction | ✅ Supported | ✅ Supported |
| Intrinsic sizing | ✅ Implemented | ✅ Implemented |
| Performance | Good for simple layouts | Optimized for all cases |
Best Practices
Use VStack When:
- You need simple vertical layouts
- Learning how layout systems work
- Building educational projects
- Spacing between children is uniform
- You need precise control over spacing (using
spacingparam)
Use Column Instead When:
- You need baseline alignment
- Performance is critical with many children
- You rely on standard Flutter widgets that expect
Column
Related Components
- ZStack - For layered layouts
- PrimitiveCard - Common VStack child
Source Code
View the complete implementation in the GitHub repository .