I am new to the flutter world. For learning purposes, I am trying to create a dummy app and while doing so I came across a design and I am wondering how can I achieve this by making my design responsive across devices?
You can use Column
with Flexible
to set ratios between two Container
(Blue and White in your example).
Put the button between containers and use Transform.translate
to offset it for half it's height in a negative direction. This will put it on top of the blue Conainer
.
import 'package:flutter/material.dart';
void main() => runApp(MyApp());
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) => MaterialApp(home: MyPage());
}
class MyPage extends StatefulWidget {
@override
_MyPageState createState() => _MyPageState();
}
class _MyPageState extends State<MyPage> with WidgetsBindingObserver {
@override
Widget build(BuildContext context) {
return Scaffold(
body: SafeArea(
child: _buildColumn(),
),
);
}
Widget _buildColumn() => Column(
crossAxisAlignment: CrossAxisAlignment.stretch,
children: [
// First blue container
_buildTopContainer(),
// Button with offset
_buildMidContainerWithButton(),
// Bottom white container
_buildBottomContainer(),
],
);
Widget _buildTopContainer() => Flexible(
flex: 10,
child: Container(
color: Colors.blue[900],
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Text(
'Top container',
style: TextStyle(
fontSize: 17.0,
fontWeight: FontWeight.w600,
color: Colors.white,
),
),
],
),
),
);
Widget _buildMidContainerWithButton() {
final buttonHeight = 50.0;
return Stack(
children: [
// Use same background color like the second container
Container(height: buttonHeight, color: Colors.white),
// Translate the button
Transform.translate(
offset: Offset(0.0, -buttonHeight / 2.0),
child: Center(
child: GestureDetector(
onTap: () { /* do stuff */ },
child: Container(
height: buttonHeight,
decoration: BoxDecoration(
color: Colors.orange[400],
borderRadius: BorderRadius.circular(buttonHeight / 2.0),
boxShadow: [
BoxShadow(
blurRadius: 16.0,
offset: Offset(0.0, 6.0),
color: Colors.black.withOpacity(0.16),
),
],
),
padding: const EdgeInsets.fromLTRB(24.0, 3.0, 24.0, 0.0),
child: Row(
mainAxisSize: MainAxisSize.min,
children: [
Icon(
Icons.photo_camera_outlined,
size: 20.0,
color: Colors.white,
),
Padding(
padding: const EdgeInsets.only(left: 8.0),
child: Text(
'Use camera',
style: TextStyle(
fontSize: 17.0,
fontWeight: FontWeight.w600,
color: Colors.white,
),
),
),
],
),
),
),
),
),
],
);
}
Widget _buildBottomContainer() => Flexible(
flex: 5,
child: Container(
color: Colors.white,
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Text(
'Bottom container',
style: TextStyle(
fontSize: 17.0,
fontWeight: FontWeight.w600,
color: Colors.black54,
),
),
]),
),
);
}