How to make a L-shape layout with Row and Column? - flutter

I would like to make the following layout within a Card widget (card within Sized Box to control the height):
layout description is:
Blue : height: same as Card's height, width: fixed
Green: height: fixed, width: remaining width of the card
Purple: height: remaining height of the card, width: fixed
Pink: height: remaining height of the card, width: remaining width of the card
Thanks in advance.

The code you are looking for is below
SizedBox(
height: 100,
child: Row(
children: [
Container(width: 100,color: Colors.blue),
Expanded(
child: Column(
children: [
Container(height: 30,color: Colors.green,),
Expanded(
child: Row(
children: [
Container(width: 100,color: Colors.purple),
Expanded(child:
Container(color: Colors.pinkAccent),)
],
),
),
],
),
)
],
),
),
Output

This will work regardless of the height/width available (it is responsive).
class MyWidget extends StatelessWidget {
const MyWidget({super.key});
#override
Widget build(BuildContext context) {
return AspectRatio(
aspectRatio: 7 / 2,
child: Row(
children: [
const Flexible(
flex: 2,
child: SizedBox.expand(
child: ColoredBox(color: Colors.blue),
),
),
Flexible(
flex: 5,
child: SizedBox.expand(
child: Column(
mainAxisAlignment: MainAxisAlignment.start,
children: [
const Flexible(
flex: 1,
child: ColoredBox(
color: Colors.green,
child: SizedBox.expand(),
),
),
Flexible(
flex: 4,
child: Row(
children: const [
Flexible(
flex: 3,
child: SizedBox.expand(
child: ColoredBox(color: Colors.purple),
),
),
Flexible(
flex: 4,
child: SizedBox.expand(
child: ColoredBox(
color: Color.fromARGB(255, 249, 139, 176)),
),
),
],
),
),
],
),
),
),
],
),
);
}
}
Output:

Related

Align children with first child in Column

How can I align my widget to take the same width as ClipRect image?
Right now it overflows in my screen. Find attached how it is and how I desire my output would be.
Is it possible to center it within the red lines I drew?
Widget build(BuildContext context) {
final mainChildKey = GlobalKey();
return Flexible(
child: Column(
children: <Widget>[
ColumnWithMainChild(
mainChildKey: mainChildKey,
children: [
ClipRRect(
borderRadius: BorderRadius.circular(8),
child: Image.network(
imgparam,
width: 350,
height: 200,
fit: BoxFit.cover,
),
),
Padding(
padding: EdgeInsetsDirectional.fromSTEB(0, 8, 0, 8),
child: Center(
child: Column(
mainAxisSize: MainAxisSize.min,
children: [
Row(
children: [
Text(
'Good with children: $param_good_children',
),
GFProgressBar(
width: 150,
percentage: 0.3,
backgroundColor: Colors.pink,
progressBarColor: Colors.red,
)
],
),
Divider(),
Text(
'Good with children: $param_good_children',
),
],
),
),
),
],
),
]));
}
}
Do the following Changes
Set Padding to Parent column
Set width of NetworkImage to double.infinity
Wrap your Progress Bar with Flexible
Code:
Widget build(BuildContext context) {
final mainChildKey = GlobalKey();
return Scaffold(
appBar: AppBar(),
body: Padding( // Set Padding to Paren
padding: const EdgeInsets.symmetric(vertical: 15, horizontal: 10),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
ClipRRect(
borderRadius: BorderRadius.circular(8),
child: Image.network(
"https://images.unsplash.com/photo-1474922651267-219b23864ae8?ixlib=rb-1.2.1&ixid=MnwxMjA3fDB8MHxwaG90by1wYWdlfHx8fGVufDB8fHx8&auto=format&fit=crop&w=870&q=80",
width: double.infinity, // Set width of NetworkImage to double.infinity
height: 200,
fit: BoxFit.cover,
),
),
Padding(
padding: const EdgeInsetsDirectional.fromSTEB(0, 8, 0, 8),
child: Center(
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
mainAxisSize: MainAxisSize.min,
children: [
Row(
children: [
const Text(
'Good with children: 5',
),
Flexible( //Wrap your Progress Bar with Flexible
child: GFProgressBar(
width: 150,
percentage: 0.3,
backgroundColor: Colors.pink,
progressBarColor: Colors.red,
),
)
],
),
const Divider(),
const Text(
'Good with children: 5',
),
],
),
),
),
]),
),
);
}
Output:

Flutter: Nested row in column, how to fill row without expanding parent column

This is what I have:
source code:
Container(
width: 150,
height: 150,
color: Colors.grey,
child: Center(
child: Column(
mainAxisSize: MainAxisSize.min,
children: [
Container(
height: 100,
width: 100,
color: Colors.green,
),
Row(
mainAxisSize: MainAxisSize.min,
children: [
Container(
child: Text('text'),
color: Colors.blue,
),
Container(
child: Text('text'),
color: Colors.red,
),
],
),
],
),
),
),
How can I make the blue and red container to match the green container's width without making them larger as the green container?
this is what I want to get without using a fixed with for the containers inside the row. Also I have more than one element in the column and I don't want to use fixed sizes.
If the size if fixed then you can add a width to the container which are wrap with the row widget.
The reason i gave width 50 is beacause the parent container is having width of 100 already so remaning width are given to containers
Container(
width: 150,
height: 150,
color: Colors.grey,
child: Column(
mainAxisSize: MainAxisSize.min,
children: [
Container(
height: 100,
width: 100,
color: Colors.green,
),
Row(
mainAxisSize: MainAxisSize.min,
children: [
Container(
width: 50,
child: Text('text'),
color: Colors.blue,
),
Container(
width: 50,
child: Text('text'),
color: Colors.red,
),
],
),
],
),
),
You can use flexible widget to give row fixible width
Container(
width: 150,
height: 150,
color: Colors.grey,
child: Center(
child: Column(
mainAxisSize: MainAxisSize.min,
children: [
Container(
height: 100,
width: 100,
color: Colors.green,
),
Container(
width: 100,
child: Row(
children: [
Flexible(
flex: 1,
fit: FlexFit.tight,
child: Container(
child: Text('text'),
color: Colors.blue,
),
),
Flexible(
flex: 1,
fit: FlexFit.tight,
child: Container(
child: Text('text'),
color: Colors.red,
),
),
],
),
),
],
),
),
)
Container(
width: 150,
height: 150,
color: Colors.grey,
child: Center(
child: Column(
mainAxisSize: MainAxisSize.min,
children: [
Container(
height: 100,
width: 100,
color: Colors.green,
),
Container(
width: 100,
Row(
mainAxisSize: MainAxisSize.min,
children: [
Expanded(
child:
Container(
child: Text('text'),
color: Colors.blue,
),
),
Expanded(
child:
Container(
child: Text('text'),
color: Colors.red,
),
),
],
),
),
],
),
),
),
You can wrap only children of Row with Expanded widget.
Try this, you have to add Exapnded to the childeren of row widgets
Container(
padding: EdgeInsets.all(16),
color: Colors.grey,
child: Column(
mainAxisSize: MainAxisSize.min,
crossAxisAlignment: CrossAxisAlignment.stretch,
children: [
Container(
color: Colors.green,
child: Text('Hdddfhlsd', style: primaryTextStyle()),
),
Row(
mainAxisSize: MainAxisSize.max,
children: [
Expanded(
child: Container(
child: Text('text'),
color: Colors.blue,
),
),
Expanded(
child: Container(
child: Text('text'),
color: Colors.red,
),
),
],
)
],
),
)
**Replace your container by this **
Container(
width: 150,
height: 150,
color: Colors.grey,
child: Center(
child: Column(
mainAxisSize: MainAxisSize.min,
children: [
Container(
width: 100,
child: Column(
children: [
Container(
height: 100,
width: 100,
color: Colors.green,
),
Row(
mainAxisSize: MainAxisSize.min,
children: [
Expanded(
child: Container(
child: Text('text'),
color: Colors.blue,
),
),
Expanded(
child: Container(
child: Text('text'),
color: Colors.red,
),
),
],
)
],
),
),
],
),
),
)

Flutter layout within a card

Im trying to create the following layout within a flutter card within a list builder.. (colours are for display purpose only)
However, its ending up like :-
Ive tried multiple variations using Cross axis (Throws errors), stretch, Expanded etc, but unfortunately i'm not getting very far.
This is what i have so far :-
return Container(
child: Card(
margin: EdgeInsets.only(bottom: 20.0),
shape: ContinuousRectangleBorder(
side: BorderSide(
width: 1.0,
color: Colors.white10,
)),
elevation: 1.0,
child: InkWell(
onTap: () => print("ciao"),
child: Column(
crossAxisAlignment:
CrossAxisAlignment.stretch, // add this
children: [
Image.memory(base64Decode(data[index].thumb_image),
// width: 300,
height: 150,
fit: BoxFit.fill),
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
Expanded(
child: Container(
color: Colors.red,
child: Column(
crossAxisAlignment:
CrossAxisAlignment.start,
children: [
Text(
'Title',
textAlign: TextAlign.left,
),
Text('Description'),
],
),
),
),
Expanded(
child: Container(
color: Colors.blue,
child: Column(
crossAxisAlignment: CrossAxisAlignment.end,
children: [
Text('12hs 8mins'),
],
),
))
],
),
Text('1000')
],
),
),
),
);
Adding a container that encapsulates your red and blue widgets helps the case. I added a height of 50 on the container that encapsulates the widgets.
void main() {
runApp(
MaterialApp(
home: MyWidget(),
),
);
}
class MyWidget extends StatelessWidget {
#override
Widget build(BuildContext context) {
return Scaffold(
body: Container(
child: Card(
margin: EdgeInsets.only(bottom: 20.0),
shape: ContinuousRectangleBorder(
side: BorderSide(
width: 1.0,
color: Colors.white10,
)),
elevation: 1.0,
child: InkWell(
onTap: () => print("ciao"),
child: Column(
crossAxisAlignment:
CrossAxisAlignment.stretch, // add this
children: [
Expanded(
child: Container(
color: Colors.green,
child: Column(
crossAxisAlignment:
CrossAxisAlignment.start,
children: [
Text(
'Title',
textAlign: TextAlign.left,
),
Text('Description'),
],
),
),
),
Container(
height: 50,
child: Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
Expanded(
child: Container(
color: Colors.red,
child: Column(
crossAxisAlignment:
CrossAxisAlignment.start,
children: [
Text(
'Title',
textAlign: TextAlign.left,
),
Text('Description'),
],
),
),
),
Expanded(
child: Container(
// MediaQuery.of(context).size.width
color: Colors.blue,
child: Column(
crossAxisAlignment: CrossAxisAlignment.end,
children: [
Text('12hs 8mins'),
],
),
))
],
),),
Text('1000')
],
),
),
),
),
);
}
}
Here's a solution with as much flexibility that I could think of:
class Home extends StatelessWidget {
#override
Widget build(BuildContext context) {
return Column(
children: [
Expanded(
child: Container(
color: Colors.green,
alignment: Alignment.center,
child: Text('Top'),
),
),
Container(
height: 100,
child: Row(
children: [
Flexible(
flex: 3,
child: Container(
color: Colors.blue,
alignment: Alignment.center,
child: Text('Bottom Left'),
)
),
Flexible(
flex: 1,
child: Container(
color: Colors.orange,
alignment: Alignment.center,
child: Text('Bottom Right'),
),
),
],
),
)
],
);
}
}
Which will look like this:

Flutter Layout with Squares Only inside Variable-Height Containers

I want to try and create a layout of variable-height, but will take up the full width of the screen. I want 2 big squares on the left, with 2 little squares on the right of the squares as needed for each big square on the left. See the purple picture for details.
However, I can't seem to be able to do this where I guarantee the inner widgets and components will be squares. Is there a way to achieve this?
If this is possible, is it possible for me to also achieve the ability to drag and rearrange (scaling as I rotate the squares back and forth as well too)? I'm trying to achieve that type of layout and the ability to rotate from each one of the 6 pictures and it will scale correctly as needed in that aspect (or the ability to drag and drop to rearrange each of the pictures).
Help would be greatly appreciated! I showed what I did below, but it doesn't seem to work to even have square items inside of the variable-height container.
return Container(
child: AspectRatio(
aspectRatio: 1.0,
child: Row(
mainAxisAlignment: MainAxisAlignment.start,
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
Expanded(
flex: 7,
child: Column(
children: <Widget>[
Expanded(
flex: 1,
child: Container(
color: Colors.grey,
),
),
Expanded(
flex: 1,
child: Container(
color: Colors.green,
),
),
],
)),
Expanded(
flex: 3,
child: Column(
mainAxisAlignment: MainAxisAlignment.start,
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
Expanded(
flex: 3,
child: Container(
color: Colors.orange,
),
),
Expanded(
flex: 3,
child: Container(
color: Colors.red,
),
),
Expanded(
flex: 3,
child: Container(
color: Colors.orange,
),
),
Expanded(
flex: 3,
child: Container(
color: Colors.red,
),
)
],
),
)
],
),
),
);
Please try this code. You should start from here. It is responsive, you just need to work more on the alignment when the screen is too small
import 'package:flutter/material.dart';
void main() {
runApp(MyApp());
}
class MyApp extends StatelessWidget {
#override
Widget build(BuildContext context) {
return MaterialApp(
theme: ThemeData.light(),
debugShowCheckedModeBanner: false,
home: Scaffold(
body: Center(
child: MyWidget(),
),
),
);
}
}
class MyWidget extends StatelessWidget {
#override
Widget build(BuildContext context) {
return FittedBox(
child: Center(
child: Container(
height: MediaQuery.of(context).size.height,
width: MediaQuery.of(context).size.width,
padding: EdgeInsets.symmetric(vertical: 24.0, horizontal: 12.0),
child: Column(
children: <Widget>[
Expanded(
child: Row(
children: <Widget>[
Expanded(
flex: 7,
child: _buildSquare(Colors.purple),
),
SizedBox(width: 12.0),
Expanded(
flex: 3,
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Expanded(
child: Align(
alignment: Alignment.bottomCenter,
child: _buildSquare(Colors.purple),
),
),
SizedBox(height: 12.0),
Expanded(
child: _buildSquare(Colors.purple),
),
],
),
),
],
),
),
SizedBox(height: 12.0),
Expanded(
child: Row(
children: <Widget>[
Expanded(
flex: 7,
child: _buildSquare(Colors.purple),
),
SizedBox(width: 12.0),
Expanded(
flex: 3,
child: Column(
children: [
Expanded(
child: _buildSquare(Colors.purple),
),
SizedBox(height: 12.0),
Expanded(
child: _buildSquare(Colors.purple),
),
],
),
),
],
),
),
],
),
),
),
);
}
Widget _buildSquare(Color color) {
return Center(
child: AspectRatio(
aspectRatio: 1.0,
child: Container(
decoration: BoxDecoration(
color: color,
border: Border.all(color: Colors.black, width: 3.0)),
),
),
);
}
}

Flutter Design for different screen sizes

I was tried my app on the phone and on the tablet. The design looks bad if the design is good on the other screen. I have shared an image that phone and tablet so you can see what design looks different when using different screen sizes.How can I set my design on all different screen sizes with Flutter?
My code :
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:flutter/widgets.dart';
void main() {
runApp(Myapp());
}
class Myapp extends StatelessWidget {
Widget build(BuildContext context) {
return MaterialApp(
theme: ThemeData(primarySwatch: Colors.red),
debugShowCheckedModeBanner: false,
home: Scaffold(
appBar: AppBar(
centerTitle: true,
title: Text(
"The Bar ",
style: TextStyle(
color: Colors.white,
fontSize: 28.0,
),
),
),
floatingActionButton: FloatingActionButton(
splashColor: Colors.green,
child: Icon(
Icons.mouse,
color: Colors.white,
),
onPressed: () {
print("You was clicked the button!");
},
),
body: Column(
mainAxisSize: MainAxisSize.max,
children: <Widget>[
Text(
"Kinds of Butoons and Images",
style: TextStyle(fontSize: 26, color: Colors.blue),
textAlign: TextAlign.center,
),
Container(
child: Expanded(
flex: 1,
child:Column(
children: <Widget>[
Container(
child: Row(
children: <Widget>[
Expanded(
child: Container(
margin: EdgeInsets.fromLTRB(10, 10, 10, 10),
child: Row(
children: <Widget>[
Container(
child: Expanded(
flex: 1,
child: Container(
margin: EdgeInsets.fromLTRB(0, 0, 10, 0),
child: Column(
children: <Widget>[
CircleAvatar(
backgroundImage: AssetImage("assets/images/test.jpg"),
radius: 140,
),
Text(
"X",
),
],
),
),
),
),
Container(
child: Expanded(
flex: 1,
child: Container(
margin: EdgeInsets.fromLTRB(0, 0, 10, 0),
child: Column(
children: <Widget>[
Image(
image: AssetImage(
"assets/images/test.jpg"),
),
Text(
"X",
),
],
),
),
),
),
Container(
child: Expanded(
flex: 1,
child: Container(
margin: EdgeInsets.fromLTRB(5, 0, 5, 0),
child: Column(
children: <Widget>[
Image(
image: AssetImage(
"assets/images/test.jpg"),
),
Text(
"X",
),
],
),
),
),
),
],
),
),
),
],
),
),
],
),
),
),
Container(
child: Expanded(
flex: 1,
child:Column(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: <Widget>[
Container(
child: Row(
children: <Widget>[
Expanded(
child: Container(
margin: EdgeInsets.fromLTRB(10, 10, 10, 10),
child: Row(
children: <Widget>[
Container(
child: Expanded(
flex: 1,
child: Container(
margin: EdgeInsets.fromLTRB(0, 0, 10, 0),
child: Column(
children: <Widget>[
CircleAvatar(
backgroundImage: AssetImage("assets/images/test.jpg"),
radius: 140,
),
Text(
"X",
),
],
),
),
),
),
Container(
child: Expanded(
flex: 1,
child: Container(
margin: EdgeInsets.fromLTRB(0, 0, 10, 0),
child: Column(
children: <Widget>[
Image(
image: AssetImage(
"assets/images/test.jpg"),
),
Text(
"X",
),
],
),
),
),
),
Container(
child: Expanded(
flex: 1,
child: Container(
margin: EdgeInsets.fromLTRB(5, 0, 5, 0),
child: Column(
children: <Widget>[
Image(
image: AssetImage(
"assets/images/test.jpg"),
),
Text(
"X",
),
],
),
),
),
),
],
),
),
),
],
),
),
],
),
),
),
],
),
),
);
}
}
To limit CircleAvatar's height, use LayoutBuilder and ConstrainedBox:
LayoutBuilder(
builder: (context, constraints) {
return ConstrainedBox(
constraints: BoxConstraints(
maxHeight: constraints.maxWidth,
maxWidth: constraints.maxWidth
),
child: CircleAvatar(
backgroundImage: NetworkImage('...'),
radius: 140,
),
);
}
),