- Buat project Flutter baru dan berikan nama yang sesuai, misalnya wisata_bandung. Hapus kode aplikasi counter yang diberikan ketika project dibuat.
- Tuliskan kode dasar yang menampilkan widget MaterialAppseperti berikut:
- import 'package:flutter/material.dart';
- void main() => runApp(MyApp());
- class MyApp extends StatelessWidget {
- @override
- Widget build(BuildContext context) {
- return MaterialApp(
- title: 'Wisata Bandung',
- theme: ThemeData.dark(),
- );
- }
- }
Di sini karena aplikasi kita akan bernuansa gelap maka kita akan menggunakan tema dark yang bisa diatur melalui parameter theme pada MaterialApp.
- Lalu kita akan membuat kode untuk susunan widget sesuai diagram yang telah kita buat. Untuk membuat kode kita lebih rapi kita akan membuat kelas Stateless Widget baru untuk menampung kode tampilan kita. Mari namakan kelas ini DetailScreen.
- class DetailScreen extends StatelessWidget {
- @override
- Widget build(BuildContext context) {
- return Scaffold();
- }
- }
Jangan lupa untuk menambahkan widget DetailScreen sebagai home dari MaterialApp.
- class MyApp extends StatelessWidget {
- @override
- Widget build(BuildContext context) {
- return MaterialApp(
- title: 'Wisata Bandung',
- theme: ThemeData.dark(),
- home: DetailScreen(),
- );
- }
- }
- Sesuai diagram di atas, kita akan menyusun beberapa widget secara vertikal sehingga kita perlu menggunakan widget Column.
- class DetailScreen extends StatelessWidget {
- @override
- Widget build(BuildContext context) {
- return Scaffold(
- body: Column(),
- );
- }
- }
Jalankan aplikasi Anda. Saat ini device atau emulator Anda memang masih belum menampilkan apa pun. Namun, kita akan memanfaatkan fitur hot reload untuk melihat perubahan-perubahan yang akan kita lakukan ke depan.
- Komponen pertama yang akan kita buat adalah bagian judul dari halaman. Tentunya untuk menampilkan teks kita akan menggunakan widget Text.
- class DetailScreen extends StatelessWidget {
- @override
- Widget build(BuildContext context) {
- return Scaffold(
- body: Column(
- children: <Widget>[
- Text('Farm House Lembang'),
- ],
- ),
- );
- }
- }
- Ketika Anda menyimpan project atau menjalankan hot reload, tampilan aplikasi Anda sekarang mungkin tidak sesuai dengan keinginan, seperti teks terlalu ke atas dan juga terlalu kecil.
Untuk itulah kita perlu membungkus widget Text ke dalam Container supaya kita dapat memberikan property seperti margin atau padding. Jika Anda menggunakan IDE Android Studio, Anda dapat memanfaatkan shortcut Alt+Enter untuk membungkus widget ke widget lain. - Tambahkan margin atas supaya teks memiliki jarak terhadap bagian atas layar.
- class DetailScreen extends StatelessWidget {
- @override
- Widget build(BuildContext context) {
- return Scaffold(
- body: Column(
- children: <Widget>[
- Container(
- margin: EdgeInsets.only(top: 16.0),
- child: Text('Farm House Lembang'),
- ),
- ],
- ),
- );
- }
- }
Pada kode di atas kita hanya memberikan margin atas sebesar sebesar 16.0. Anda dapat memanfaatkan metode EdgeInsets lain seperti all() untuk memberikan margin ke semua sisi atau symmetric() apabila Anda ingin memberikan margin ke sisi vertikal atau horizontal.
- Selanjutnya, sesuai contoh kita akan membuat teks judul berada di tengah. Tambahkan parameter atau properti textAlign pada widget Text.
- Container(
- margin: EdgeInsets.only(top: 16.0),
- child: Text(
- 'Farm House Lembang',
- textAlign: TextAlign.center,
- style: TextStyle(
- fontSize: 30.0,
- fontWeight: FontWeight.bold,
- ),
- ),
- ),
Lakukan hot reload. Tidak ada perubahan, apa sebabnya? Jika menggunakan Android Studio Anda dapat memanfaatkan fitur Flutter Inspector untuk melihat layout widget di dalam aplikasi.
Dari gambar di atas bisa kita lihat ternyata layout aplikasi kita tidak penuh hingga seluruh halaman. Ini disebabkan sisi horizontal dari Column hanya menyesuaikan dengan konten yang ada di dalamnya. Untuk memaksimalkan ukuran lebar dari Column, tambahkan kode berikut:- body: Column(
- crossAxisAlignment: CrossAxisAlignment.stretch,
- children: <Widget>[
- Container(
- margin: EdgeInsets.only(top: 16.0),
- child: Text(
- 'Farm House Lembang',
- textAlign: TextAlign.center,
- style: TextStyle(
- fontSize: 30.0,
- fontWeight: FontWeight.bold,
- ),
- ),
- ),
- ],
- ),
Parameter crossAxisAlignment berguna untuk mengatur alignment horizontal dari Column. Selain itu Column juga memiliki parameter mainAxisAlignment yang berfungsi untuk mengatur alignment secara vertikal (alignment utama). Kedua parameter ini juga berlaku sebaliknya untuk widget Row.
- Setelah menyelesaikan judul, selanjutnya kita akan membuat bagian kedua yaitu informasi dari tempat wisata.
Seperti yang terlihat kita perlu menyusun widget secara horizontal dan vertikal. Mari tambahkan child kedua dari Column dengan sebuah Container berisi Row. Tambahkan juga margin pada sisi atas dan bawah untuk memberikan jarak antar widget.- class DetailScreen extends StatelessWidget { @override
- Widget build(BuildContext context) {
- return Scaffold(
- body: Column(
- crossAxisAlignment: CrossAxisAlignment.stretch,
- children: <Widget>[
- Container(...),
- Container(
- margin: EdgeInsets.symmetric(vertical: 16.0),
- child: Row(
- children: <Widget>[],
- ),
- ),
- ],
- ),
- );
- }
- }
- Buat widget Column untuk menyusun Icon dan Text.
- class DetailScreen extends StatelessWidget {
- @override
- Widget build(BuildContext context) {
- return Scaffold(
- body: Column(
- crossAxisAlignment: CrossAxisAlignment.stretch,
- children: <Widget>[
- Container(…),
- Container( margin: EdgeInsets.symmetric(vertical: 16.0),
- child: Row(
- children: <Widget>[
- Column(
- children: <Widget>[
- Icon(Icons.calendar_today),
- Text(‘Open Everyday’),
- ],
- ),
- ],
- ),
- ),
- ],
- ),
- );
- }
- }
- Jika Anda merasa jarak antara Icon dan Text terlalu rapat, Anda dapat menambahkan widget SizedBoxuntuk membuat “kotak” yang berguna untuk memberikan jarak.
- Column(
- children: <Widget>[
- Icon(Icons.calendar_today),
- SizedBox(height: 8.0),
- Text('Open Everyday'),
- ],
- ),
- Selanjutnya sebagai tantangan, lengkapilah informasi tempat wisata dengan pasangan ikon dan teks sesuai contoh yang diberikan.
- Jika hanya membuat 3 Column di dalam Row, maka tampilan widget Anda akan berurutan di sisi kiri layar seperti berikut:
Bagaimana membuatnya menjadi lebih rapi? Jawabannya adalah mainAxisAlignment. Tambahkan MainAxisAlignment.spaceEvenlysebagai parameter untuk membuat masing-masing child di dalam Row memiliki jarak yang sama.
- class DetailScreen extends StatelessWidget {
- @override
- Widget build(BuildContext context) {
- return Scaffold(
- body: Column(
- crossAxisAlignment: CrossAxisAlignment.stretch,
- children: <Widget>[
- Container(…),
- Container(
- margin: EdgeInsets.symmetric(vertical: 16.0),
- child: Row(
- mainAxisAlignment: MainAxisAlignment.spaceEvenly,
- children: <Widget>[
- Column(…),
- Column(…),
- Column(…),
- ],
- ),
- ),
- ],
- ),
- );
- }
- }
- Pada langkah ini harusnya Anda sudah bisa menampilkan teks deskripsi sesuai langkah yang diberikan sebelumnya. Anda cukup menambahkan widget Container dan Textuntuk menampilkan konten deskripsi. Anda juga dapat menambahkan style sesuai selera Anda.
- Container(
- padding: EdgeInsets.all(16.0),
- child: Text(
- 'Berada di jalur utama Bandung-Lembang, Farm House menjadi objek wisata yang tidak pernah sepi pengunjung. Selain karena letaknya strategis, kawasan ini juga menghadirkan nuansa wisata khas Eropa. Semua itu diterapkan dalam bentuk spot swafoto Instagramable.',
- textAlign: TextAlign.center,
- style: TextStyle(fontSize: 16.0),
- ),
- ),
- Terakhir, kita ingin mengubah background aplikasi menjadi warna hitam. Untuk mengubah warna background, gunakan parameter yang ada pada widget Scaffold.
- class DetailScreen extends StatelessWidget {
- @override
- Widget build(BuildContext context) {
- return Scaffold(
- backgroundColor: Colors.black,
- body: Column(...),
- );
- }
- }
- Keseluruhan kode Anda akan seperti berikut
- import ‘package:flutter/material.dart’;
- void main() => runApp(MyApp());
- class MyApp extends StatelessWidget {
- @override
- Widget build(BuildContext context) {
- return MaterialApp(
- title: ‘Wisata Bandung’,
- theme: ThemeData.dark(),
- home: DetailScreen(),
- );
- }
- }
- class DetailScreen extends StatelessWidget {
- @override
- Widget build(BuildContext context) {
- return Scaffold(
- backgroundColor: Colors.black,
- body: Column(
- crossAxisAlignment: CrossAxisAlignment.stretch,
- children: <Widget>[
- Container(
- margin: EdgeInsets.only(top: 16.0),
- child: Text(
- ‘Farm House Lembang’,
- textAlign: TextAlign.center,
- style: TextStyle(
- fontSize: 30.0,
- fontWeight: FontWeight.bold,
- ),
- ),
- ),
- Container(
- margin: EdgeInsets.symmetric(vertical: 16.0),
- child: Row(
- mainAxisAlignment: MainAxisAlignment.spaceEvenly,
- children: <Widget>[
- Column(
- children: <Widget>[
- Icon(Icons.calendar_today),
- SizedBox(height: 8.0),
- Text(‘Open Everyday’),
- ],
- ),
- Column(
- children: <Widget>[
- Icon(Icons.access_time),
- SizedBox(height: 8.0),
- Text(’09:00 – 20:00′),
- ],
- ),
- Column(
- children: <Widget>[
- Icon(Icons.monetization_on),
- SizedBox(height: 8.0),
- Text(‘Rp 25.000’),
- ],
- ),
- ],
- ),
- ),
- Container(
- padding: EdgeInsets.all(16.0),
- child: Text(
- ‘Berada di jalur utama Bandung-Lembang, Farm House menjadi objek wisata yang tidak pernah sepi pengunjung. Selain karena letaknya strategis, kawasan ini juga menghadirkan nuansa wisata khas Eropa. Semua itu diterapkan dalam bentuk spot swafoto Instagramable.’,
- textAlign: TextAlign.center,
- style: TextStyle(fontSize: 16.0),
- ),
- ),
- ],
- ),
- );
- }
- }