first commit

This commit is contained in:
kicap1992
2022-10-01 00:01:41 +08:00
commit 1c6c368135
143 changed files with 5353 additions and 0 deletions

32
lib/main.dart Normal file
View File

@ -0,0 +1,32 @@
import 'package:flutter/material.dart';
import 'package:flutter_dotenv/flutter_dotenv.dart';
import 'package:flutter_easyloading/flutter_easyloading.dart';
import 'src/config/routes.dart';
import 'src/config/theme.dart';
import 'src/services/storage_service.dart';
Future main() async {
WidgetsFlutterBinding.ensureInitialized();
await dotenv.load(fileName: ".env");
StorageService storage = StorageService();
await storage.init();
runApp(const MyApp());
}
class MyApp extends StatelessWidget {
const MyApp({super.key});
// This widget is the root of your application.
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Ramalamn Tapak Tangan',
theme: ThemeInfo.getTheme(),
debugShowCheckedModeBanner: false,
initialRoute: 'splash',
routes: RoutesApp.getRoutes(),
builder: EasyLoading.init(),
);
}
}

View File

@ -0,0 +1,13 @@
import 'package:flutter/cupertino.dart';
import '../pages/index.dart';
import '../pages/splash_screen.dart';
class RoutesApp {
static getRoutes() {
return {
'splash': (BuildContext context) => const SplashScreen(),
'index': (BuildContext context) => const IndexPage(),
};
}
}

17
lib/src/config/theme.dart Normal file
View File

@ -0,0 +1,17 @@
import 'package:flutter/material.dart';
import 'package:google_fonts/google_fonts.dart';
class ThemeInfo {
static const Color primary = Color.fromARGB(255, 217, 112, 112);
static const Color background = Color(0xffF5F5F5);
static const Color myGrey = Colors.grey;
static const Color negroTexto = Color(0xff4E4E4E);
static ThemeData getTheme() {
return ThemeData(
backgroundColor: background,
primaryColor: primary,
fontFamily: GoogleFonts.roboto().fontFamily,
);
}
}

View File

@ -0,0 +1,89 @@
import 'dart:io';
import 'dart:typed_data';
import 'package:cek_tapak_tangan/src/config/theme.dart';
import 'package:flutter/material.dart';
import 'package:image_picker/image_picker.dart';
class AmbilFoto extends StatefulWidget {
const AmbilFoto({Key? key}) : super(key: key);
@override
State<AmbilFoto> createState() => _AmbilFotoState();
}
class _AmbilFotoState extends State<AmbilFoto> {
bool _hasFoto = false; // if has foto
String? _imgPath; // path to foto
final ImagePicker _picker = ImagePicker();
XFile? _imageFile; // file to foto
Uint8List? imagebytes;
Future<void> onImageButtonPressed() async {
try {
final XFile? pickedFile =
await _picker.pickImage(source: ImageSource.camera);
_imageFile = pickedFile;
final file = File(_imageFile!.path);
if (file.existsSync()) {
final Uint8List bytes = await file.readAsBytes();
setState(() {
_imgPath = _imageFile!.path.toString();
imagebytes = bytes;
_hasFoto = true;
});
// popDialog();
// _showTambahLaporan();
}
} catch (e) {
// dev.e(e);
}
}
@override
Widget build(BuildContext context) {
return Scaffold(
body: Padding(
padding: EdgeInsets.only(
right: MediaQuery.of(context).size.height * 0.1,
left: MediaQuery.of(context).size.height * 0.1,
),
child: Center(
child: Column(
mainAxisSize: MainAxisSize.min,
children: [
Text(
"Silakan Ambil Foto Telapak Anda",
textAlign: TextAlign.center,
style: TextStyle(
color: ThemeInfo.primary,
fontSize: 30,
fontWeight: FontWeight.bold,
fontStyle: FontStyle.italic,
),
),
SizedBox(
height: 10,
),
ElevatedButton(
style: ElevatedButton.styleFrom(
backgroundColor: ThemeInfo.primary,
),
onPressed: () {
onImageButtonPressed();
},
child: Text(
"Gambar Telapak Tangan",
style: TextStyle(
fontStyle: FontStyle.italic,
),
),
),
],
),
),
),
);
}
}

61
lib/src/pages/index.dart Normal file
View File

@ -0,0 +1,61 @@
import 'package:cek_tapak_tangan/src/pages/ambil_foto.dart';
import 'package:cek_tapak_tangan/src/pages/profile.dart';
import 'package:flutter/material.dart';
import 'package:logger/logger.dart';
import '../widgets/appbar.dart';
import '../widgets/bottombar.dart';
import 'list_ensiklopedia.dart';
class IndexPage extends StatefulWidget {
const IndexPage({super.key});
@override
State<IndexPage> createState() => _IndexPageState();
}
class _IndexPageState extends State<IndexPage> {
final dev = Logger();
int _indexSelected = 1;
// late String formatted;
final List<String> _headerName = [
'Ensiklopedia ',
'Halaman Ramalan',
'Halaman Profil',
];
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: PreferredSize(
preferredSize:
Size.fromHeight(MediaQuery.of(context).size.height * 0.07),
child: AppBarWidget(
header: _headerName[_indexSelected],
autoLeading: false,
),
),
body: tabWidget(context),
bottomNavigationBar: BottomBarWidget(
indexSelected: _indexSelected,
onTap: (index) {
setState(() {
_indexSelected = index;
});
},
),
);
}
tabWidget(BuildContext context) {
switch (_indexSelected) {
case 0:
return const ListPage();
case 1:
return const AmbilFoto();
case 2:
return const ProfilPage();
}
}
}

View File

@ -0,0 +1,134 @@
import 'package:cek_tapak_tangan/src/widgets/bounce_scoller.dart';
import 'package:flutter/material.dart';
import '../config/theme.dart';
class ListPage extends StatelessWidget {
const ListPage({super.key});
@override
Widget build(BuildContext context) {
return Scaffold(
body: BounceScrollerWidget(
children: [
SizedBox(
height: 20,
),
Column(
mainAxisAlignment: MainAxisAlignment.center,
mainAxisSize: MainAxisSize.min,
children: [
Column(
children: [
Padding(
padding: const EdgeInsets.all(10),
child: Container(
padding: const EdgeInsets.all(10),
alignment: Alignment.center,
width: double.infinity,
decoration: BoxDecoration(
color: ThemeInfo.myGrey,
borderRadius: BorderRadius.circular(10),
boxShadow: const [
BoxShadow(
color: ThemeInfo.myGrey,
blurRadius: 10,
spreadRadius: 5,
),
],
),
child: Row(
crossAxisAlignment: CrossAxisAlignment.center,
mainAxisAlignment: MainAxisAlignment.spaceAround,
children: [
Expanded(
flex: 4,
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
mainAxisAlignment: MainAxisAlignment.center,
children: [
Text(
"tanggal",
style: const TextStyle(
color: ThemeInfo.negroTexto,
fontSize: 15,
fontWeight: FontWeight.bold,
),
),
Text(
"asdasd",
style: const TextStyle(
color: ThemeInfo.negroTexto,
fontSize: 15,
fontWeight: FontWeight.bold,
),
),
],
),
),
Expanded(
flex: 5,
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
mainAxisAlignment: MainAxisAlignment.center,
children: [
Text(
'',
style: const TextStyle(
color: ThemeInfo.negroTexto,
fontSize: 15,
fontWeight: FontWeight.bold,
),
),
Text(
// lorem ipsum dolor sit amet consectetur adipisicing elit.
'',
overflow: TextOverflow.ellipsis,
maxLines: 2,
style: const TextStyle(
color: ThemeInfo.negroTexto,
fontSize: 10,
fontWeight: FontWeight.bold,
),
),
],
),
),
Expanded(
flex: 3,
child: Container(
width: 40,
height: 40,
decoration: const BoxDecoration(
color: ThemeInfo.primary,
shape: BoxShape.circle,
boxShadow: [
BoxShadow(
color: ThemeInfo.myGrey,
blurRadius: 10,
spreadRadius: 5,
),
],
),
child: IconButton(
onPressed: () {
// dev.i("heheheh");
// showLaporan(context);
},
icon: const Icon(Icons.read_more_outlined),
),
),
),
],
),
),
)
],
),
],
),
],
),
);
}
}

141
lib/src/pages/profile.dart Normal file
View File

@ -0,0 +1,141 @@
import 'package:flutter/material.dart';
import '../config/theme.dart';
import '../widgets/bounce_scoller.dart';
class ProfilPage extends StatefulWidget {
const ProfilPage({Key? key}) : super(key: key);
@override
State<ProfilPage> createState() => _ProfilPageState();
}
class _ProfilPageState extends State<ProfilPage> {
@override
Widget build(BuildContext context) {
return BounceScrollerWidget(
children: [
Column(
crossAxisAlignment: CrossAxisAlignment.center,
children: [
const SizedBox(
height: 20,
),
Container(
padding: const EdgeInsets.all(5),
alignment: Alignment.center,
height: 100,
width: 100,
decoration: const BoxDecoration(
shape: BoxShape.circle,
color: Colors.white,
// borderRadius: BorderRadius.circular(100),
image: DecorationImage(
image: AssetImage('assets/loading.gif'),
fit: BoxFit.fitHeight,
),
boxShadow: [
BoxShadow(
color: ThemeInfo.myGrey,
blurRadius: 10,
spreadRadius: 5,
),
],
),
child: Image.asset(
'assets/profile_blank.png',
fit: BoxFit.cover,
),
),
Padding(
padding: const EdgeInsets.all(10),
child: Text(
"asdsadsa",
style: const TextStyle(
fontSize: 20,
fontWeight: FontWeight.bold,
color: ThemeInfo.negroTexto,
),
),
),
_DetailParent(),
],
),
],
);
}
}
class _DetailParent extends StatelessWidget {
const _DetailParent({
Key? key,
}) : super(key: key);
@override
Widget build(BuildContext context) {
return Column(
crossAxisAlignment: CrossAxisAlignment.center,
children: [
_DetailChild(
icon: Icons.person_pin,
title: "217 280 201",
),
SizedBox(
height: MediaQuery.of(context).size.height * 0.1,
)
],
);
}
}
class _DetailChild extends StatelessWidget {
const _DetailChild({
Key? key,
required this.title,
required this.icon,
}) : super(key: key);
final String title;
final IconData icon;
@override
Widget build(BuildContext context) {
return Padding(
padding: const EdgeInsets.all(10),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Padding(
padding: const EdgeInsets.only(bottom: 10),
child: Row(
crossAxisAlignment: CrossAxisAlignment.center,
children: [
Icon(
icon,
color: ThemeInfo.myGrey,
size: 40,
),
const SizedBox(
width: 20,
),
Flexible(
child: Text(
title,
maxLines: 3,
// softWrap: false,
// overflow: TextOverflow.fade,
style: const TextStyle(
fontSize: 18,
fontWeight: FontWeight.bold,
color: ThemeInfo.myGrey,
),
),
),
],
),
),
],
),
);
}
}

View File

@ -0,0 +1,73 @@
import 'package:cek_tapak_tangan/src/config/theme.dart';
import 'package:flutter/material.dart';
class SplashScreen extends StatefulWidget {
const SplashScreen({super.key});
@override
State<SplashScreen> createState() => _SplashScreenState();
}
class _SplashScreenState extends State<SplashScreen> {
@override
void initState() {
super.initState();
// initPlatformState();
// future 3 sec
Future.delayed(const Duration(seconds: 4), () async {
// await _storage.remove('userData');
Navigator.pushReplacementNamed(context, 'index');
});
}
@override
Widget build(BuildContext context) {
return Scaffold(
backgroundColor: ThemeInfo.primary,
body: Stack(
children: [
Center(
child: Image.asset(
'assets/tapak_tangan.png',
width: MediaQuery.of(context).size.width * 0.8,
height: MediaQuery.of(context).size.width * 0.8,
),
),
Positioned(
top: MediaQuery.of(context).size.height * 0.1,
left: MediaQuery.of(context).size.width * 0.1,
right: MediaQuery.of(context).size.width * 0.1,
child: Center(
child: Text(
"Ramalan \nTelapak Tangan",
textAlign: TextAlign.center,
style: TextStyle(
color: ThemeInfo.background,
fontSize: 30,
fontWeight: FontWeight.bold,
fontStyle: FontStyle.italic,
),
),
),
),
Positioned(
bottom: MediaQuery.of(context).size.height * 0.05,
left: MediaQuery.of(context).size.width * 0.1,
right: MediaQuery.of(context).size.width * 0.1,
child: Center(
child: Text(
"Created By \nKicap Karan",
textAlign: TextAlign.center,
style: TextStyle(
color: ThemeInfo.background,
fontSize: 10,
),
),
),
),
],
),
);
}
}

View File

View File

@ -0,0 +1,30 @@
import 'package:get_storage/get_storage.dart';
class StorageService {
static final StorageService _singleton = StorageService.internal();
factory StorageService() {
return _singleton;
}
StorageService.internal();
late GetStorage _storage;
init() async {
await GetStorage.init();
_storage = GetStorage();
}
Future<dynamic> read(String key) async {
return await _storage.read(key);
}
Future<void> write(String key, dynamic val) async {
return await _storage.write(key, val);
}
Future<void> remove(String key) async {
return await _storage.remove(key);
}
}

View File

@ -0,0 +1,34 @@
import 'package:flutter/material.dart';
import '../config/theme.dart';
class AppBarWidget extends StatelessWidget {
const AppBarWidget({
Key? key,
required this.header,
required this.autoLeading,
}) : super(key: key);
final String header;
final bool autoLeading;
@override
Widget build(BuildContext context) {
return AppBar(
centerTitle: true,
title: Text(
header,
style: TextStyle(
fontSize: MediaQuery.of(context).size.height * 0.03,
fontWeight: FontWeight.bold,
),
),
automaticallyImplyLeading: autoLeading,
backgroundColor: ThemeInfo.primary,
shape: const RoundedRectangleBorder(
borderRadius: BorderRadius.vertical(
bottom: Radius.circular(40),
),
),
);
}
}

View File

@ -0,0 +1,53 @@
import 'package:convex_bottom_bar/convex_bottom_bar.dart';
import 'package:flutter/material.dart';
import '../config/theme.dart';
class BottomBarWidget extends StatelessWidget {
const BottomBarWidget(
{Key? key, required this.indexSelected, required this.onTap})
: super(key: key);
final int indexSelected;
final Function(int) onTap;
@override
Widget build(BuildContext context) {
return ConvexAppBar(
// cornerRadius: 10,
initialActiveIndex: indexSelected,
disableDefaultTabController: true,
backgroundColor: ThemeInfo.primary,
items: [
TabItem(
icon: Icon(
Icons.list_alt_outlined,
color:
(indexSelected == 0) ? ThemeInfo.primary : ThemeInfo.background,
),
title: 'Ensiklopedia',
),
TabItem(
icon: Icon(
Icons.photo_camera,
color:
(indexSelected == 1) ? ThemeInfo.primary : ThemeInfo.background,
),
title: 'Ramalan',
),
TabItem(
icon: Icon(
Icons.person_outline,
color:
(indexSelected == 2) ? ThemeInfo.primary : ThemeInfo.background,
),
title: 'Profil',
),
],
elevation: 1,
onTap: (int index) {
onTap(index);
},
);
}
}

View File

@ -0,0 +1,27 @@
import 'package:flutter/material.dart';
class BounceScrollerWidget extends StatelessWidget {
final List<Widget> children;
const BounceScrollerWidget({Key? key, required this.children})
: super(key: key);
@override
Widget build(BuildContext context) {
return SingleChildScrollView(
child: SizedBox(
height: MediaQuery.of(context).size.height * 0.9,
width: MediaQuery.of(context).size.width,
child: ListView(
padding: EdgeInsets.only(
left: MediaQuery.of(context).size.height * 0.03,
right: MediaQuery.of(context).size.height * 0.03,
),
physics: const BouncingScrollPhysics(
parent: AlwaysScrollableScrollPhysics(),
),
children: children,
),
),
);
}
}