This is the 12th day of my participation in Gwen Challenge
preface
We are going to talk about Stack layout. We can call it Stack layout, also called hierarchical layout, mainly to display the overlapping layout of the plane, which can be more flexible control of the location of sub-items.
Simple to use
So let’s add three different sizes here, and see how they stack up.
Stack(
children: [
getItem(3, width: 120, height: 120, color: Colors.purple),
getItem(2, width: 80, height: 80, color: Colors.blue),
getItem(1),,)Copy the code
getItem
Except for index, all parameters are selected
/// Get the subproject (using the selection parameter)
Widget getItem(int index,
{double? width = 60.double? height = 60, Color color = Colors.orange}) {
return Container(
// Set width and height to 60
width: width,
height: height,
// Set the background color
color: color,
// Set the gap
margin: EdgeInsets.all(2),
// Center the subitem
alignment: Alignment.center,
// Set the child
child: Text('$index')); }Copy the code
See the effect
Alignment (alignment)
If you look at the source code as you can see the default value of this parameter is AlignmentDirectional topStart, but here we can still use our familiar Alignment. The topLeft to parameter Settings, is this why? Take a look at the AlignmentDirectional source code, which we looked at in the previous section
Stack(
// Center and align
alignment: Alignment.topLeft,
children: [
getItem(3, width: 120, height: 120, color: Colors.purple),
getItem(2, width: 80, height: 80, color: Colors.blue),
getItem(1),,)Copy the code
Alignment and AlignmentDirectional source
// Alignment
class Alignment extends AlignmentGeometry {
/// Creates an alignment.
///
/// The [x] and [y] arguments must not be null.
const Alignment(this.x, this.y)
: assert(x ! =null),
assert(y ! =null);
static const Alignment topLeft = Alignment(1.0.1.0);
static const Alignment center = Alignment(0.0.0.0); . }// AlignmentDirectional
class AlignmentDirectional extends AlignmentGeometry {
const AlignmentDirectional(this.start, this.y)
: assert(start ! =null),
assert(y ! =null);
static const AlignmentDirectional topStart = AlignmentDirectional(1.0.1.0);
// Consider using Alignment. Center instead
static const AlignmentDirectional center = AlignmentDirectional(0.0.0.0); . }Copy the code
We have posted the core source code above, it can be seen that they both inherit AlignmentGeometry, and then the implementation is similar, and the comments in the source code also recommend us to use Alignment instead
Various alignment effects
Here we use Alignment
Alignment.topLeft | Alignment.topCenter | Alignment.topRight |
---|---|---|
Alignment.centerLeft | Alignment.center | Alignment.centerRight |
Alignment.bottomLeft | Alignment.bottomCenter | Alignment.bottomRight |
Learn some skills
When we enter parameters such as **Alignment. BottomRight **, which is too cumbersome to input all at once, we can enter part of the prefix + the first letter of the constant, as follows
- Alignment.bottomRight => alibr
- Alignment.center => alic
Read my article and you will find that there are not only source code analysis, structure combing and various practical skills, remember to pay attention to me oh
Fit (filling method)
To demonstrate the effect, let’s add a background BgContainer (the generic component of the previous chapter wrapper)
BgContainer(
child: Stack(
/ / in the middle
alignment: Alignment.center,
// Set the default value loose
fit: StackFit.loose,
children: [
getItem(3, width: 120, height: 120, color: Colors.purple),
getItem(2, width: 80, height: 80, color: Colors.blue),
getItem(1)],),)Copy the code
Stackfit.loose (loose) – Default
Here we use DevTools for the effectWidget Inspector
To debug the layout and maybe talk about Flutter DevTools usage techniques later (no promises here, but may come back)
As you can see from the figure above, the size of the Stack depends on the largest of the subitems (i.ePurple 120
Width and height subterm)
It’s time to expand.
This doesn’t seem to be quite as expected. Shouldn’t it be possible to expand the Stack to maximum?
Currently our subitems are unpositioned, so all subclass constraints are extended to match the maximum value of the Stack
Add the position
So let’s change it a little bit and see what it looks like. Let’s look at the code
BgContainer(
child: Stack(
alignment: Alignment.center,
fit: StackFit.expand,
children: [
getItem(3, width: 120, height: 120, color: Colors.purple),
getItem(2, width: 80, height: 80, color: Colors.blue),
// This adds positioning
Positioned(
// 10 to the left
left: 10.// 10 from the top
top: 10,
child: getItem(1(), (], (), (Copy the code
Now that I see the effect,1 yellow
The subitem follows its own constraints because it adds the location, and the others2, 3,
And because no location is addedStack
The same size, the constraint is passed.
Here we temporarily do not talk about the use of positioning, the next part of our system chat
StackFit. Passthrough
So let’s see what happens
This seems to be the sameloose
What difference does it make? We can take a look at the source code and change it to the sample code below
BgContainer(
// Add a horizontal layout
child: Row(
children: [
// Add the expansion component, which can be seen in the column
Expanded(
child: Stack(
alignment: Alignment.center,
// Set the filling method to passthrough
fit: StackFit.passthrough,
children: [
getItem(3, width: 120, height: 120, color: Colors.purple),
getItem(2, width: 80, height: 80, color: Colors.blue),
Positioned(
left: 10,
top: 10,
child: getItem(1() [() [() [() [() [()Copy the code
Here we see the vsexpand
It’s a little bit different, but here we’re just expanding the width, and the height is still the height of the subterm. Because hereStack
The width constraint is the expanded screen width, which is passed directly to the child component without adding positioning, so see2, 3,
The subcomponents then change, and1
The size of the child component has not changed.
What happens if it is loose?
Alignment and subitem constraints continue for non-positioned components
A small summary
clipBehavior
Because this article is based on Flutter 2.2.1, overflow has been deprecated. Many clipping behaviors will be changed to clipBehavior in future. This is a parameter we discussed earlier in The Clipping article “The Use of various clipping widgets in Flutter”
How do we expect to crop the render when we set the size of the child to be larger than the Stack layout? Clipping or display, anti-aliasing or no aliasing?
BgContainer(
child: Stack(
alignment: Alignment.center,
fit: StackFit.passthrough,
// Set clipping behavior to hardEdge by default
clipBehavior: Clip.hardEdge,
children: [
getItem(3, width: 120, height: 120, color: Colors.purple),
getItem(2, width: 80, height: 80, color: Colors.blue),
// Set this to position the upper left corner -20
Positioned(
left: - 20,
top: - 20,
child: getItem(1(), (], (), (Copy the code
See the effect
Clip.none (not clipping) | Clip.hardEdge | AntiAlias, antiAliasWithSaveLayer |
---|---|---|
It is generally set by default and not clipping. For others, you can refer back to the clipping chapter for the differences.
So that wraps up the Stack core, and in the next video we combine the positioning component “jam, Align”, so keep your eyes on my column
Source warehouse
Based on the latest version of Flutter 🔥
- Flutter Widgets warehouse
Refer to the link
- Stack (Flutter Widget of the Week)
- Flutter-Stack
Pay attention to column
- This article has been included in the column at 👇 below, you can follow it directly
- Read more | The series continues to be updated
👏 welcome to like ➕ collect ➕ pay attention, please feel free to comment on 👇 if you have any questions, I will reply as soon as possible