step 3 : hapus ai_barcode_scanner, ai barcode, update permission_handler, flutter_map,latlong2
This commit is contained in:
126
lib/widget/chip_type.dart
Normal file
126
lib/widget/chip_type.dart
Normal file
@@ -0,0 +1,126 @@
|
||||
import 'package:flutter/material.dart';
|
||||
|
||||
import '../../app/constant.dart';
|
||||
|
||||
class ChipType extends StatelessWidget {
|
||||
ChipType(
|
||||
{super.key,
|
||||
required this.tipe,
|
||||
required this.name,
|
||||
required this.isDetailHistory});
|
||||
final int tipe;
|
||||
final String name;
|
||||
bool isDetailHistory = false;
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
switch (tipe) {
|
||||
case 5:
|
||||
return Container(
|
||||
padding: EdgeInsets.symmetric(
|
||||
horizontal: Constant.getActualX(context: context, x: 8)),
|
||||
decoration: BoxDecoration(
|
||||
color: Constant.backgroundBlue,
|
||||
borderRadius: BorderRadius.circular(6)),
|
||||
child: Text(
|
||||
name,
|
||||
overflow: TextOverflow.ellipsis,
|
||||
style: isDetailHistory
|
||||
? Constant.body1(context: context).copyWith(
|
||||
fontWeight: FontWeight.w600, color: Constant.primaryBlue)
|
||||
: Constant.caption1(context: context).copyWith(
|
||||
fontWeight: FontWeight.w600, color: Constant.primaryBlue),
|
||||
),
|
||||
);
|
||||
|
||||
case 1:
|
||||
return Container(
|
||||
padding: EdgeInsets.symmetric(
|
||||
horizontal: Constant.getActualX(context: context, x: 8)),
|
||||
decoration: BoxDecoration(
|
||||
color: Constant.backgroundOrange,
|
||||
borderRadius: BorderRadius.circular(6)),
|
||||
child: Text(
|
||||
name,
|
||||
overflow: TextOverflow.ellipsis,
|
||||
style: isDetailHistory
|
||||
? Constant.body1(context: context).copyWith(
|
||||
fontWeight: FontWeight.w600, color: Constant.primaryOrange)
|
||||
: Constant.caption1(context: context).copyWith(
|
||||
fontWeight: FontWeight.w600, color: Constant.primaryOrange),
|
||||
),
|
||||
);
|
||||
|
||||
case 3:
|
||||
return Container(
|
||||
padding: EdgeInsets.symmetric(
|
||||
horizontal: Constant.getActualX(context: context, x: 8)),
|
||||
decoration: BoxDecoration(
|
||||
color: Constant.backgroundGreen,
|
||||
borderRadius: BorderRadius.circular(6)),
|
||||
child: Text(
|
||||
name,
|
||||
overflow: TextOverflow.ellipsis,
|
||||
style: isDetailHistory
|
||||
? Constant.body1(context: context).copyWith(
|
||||
fontWeight: FontWeight.w600, color: Constant.primaryGreen)
|
||||
: Constant.caption1(context: context).copyWith(
|
||||
fontWeight: FontWeight.w600, color: Constant.primaryGreen),
|
||||
),
|
||||
);
|
||||
|
||||
case 2:
|
||||
return Container(
|
||||
padding: EdgeInsets.symmetric(
|
||||
horizontal: Constant.getActualX(context: context, x: 8)),
|
||||
decoration: BoxDecoration(
|
||||
color: Constant.backgroundPurple,
|
||||
borderRadius: BorderRadius.circular(6)),
|
||||
child: Text(
|
||||
name,
|
||||
overflow: TextOverflow.ellipsis,
|
||||
style: isDetailHistory
|
||||
? Constant.body1(context: context).copyWith(
|
||||
fontWeight: FontWeight.w600, color: Constant.primaryPurple)
|
||||
: Constant.caption1(context: context).copyWith(
|
||||
fontWeight: FontWeight.w600, color: Constant.primaryPurple),
|
||||
),
|
||||
);
|
||||
|
||||
case 4:
|
||||
return Container(
|
||||
padding: EdgeInsets.symmetric(
|
||||
horizontal: Constant.getActualX(context: context, x: 8)),
|
||||
decoration: BoxDecoration(
|
||||
color: Constant.primaryRed.withOpacity(0.25),
|
||||
borderRadius: BorderRadius.circular(6)),
|
||||
child: Text(
|
||||
name,
|
||||
overflow: TextOverflow.ellipsis,
|
||||
style: isDetailHistory
|
||||
? Constant.body1(context: context).copyWith(
|
||||
fontWeight: FontWeight.w600, color: Constant.primaryRed)
|
||||
: Constant.caption1(context: context).copyWith(
|
||||
fontWeight: FontWeight.w600, color: Constant.primaryRed),
|
||||
),
|
||||
);
|
||||
|
||||
default:
|
||||
return Container(
|
||||
padding: EdgeInsets.symmetric(
|
||||
horizontal: Constant.getActualX(context: context, x: 8)),
|
||||
decoration: BoxDecoration(
|
||||
color: Constant.backgroundBlue,
|
||||
borderRadius: BorderRadius.circular(6)),
|
||||
child: Text(
|
||||
name,
|
||||
overflow: TextOverflow.ellipsis,
|
||||
style: isDetailHistory
|
||||
? Constant.body1(context: context).copyWith(
|
||||
fontWeight: FontWeight.w600, color: Constant.primaryBlue)
|
||||
: Constant.caption1(context: context).copyWith(
|
||||
fontWeight: FontWeight.w600, color: Constant.primaryBlue),
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
248
lib/widget/custom_textfield.dart
Normal file
248
lib/widget/custom_textfield.dart
Normal file
@@ -0,0 +1,248 @@
|
||||
import 'package:flutter/material.dart';
|
||||
|
||||
import '../../app/constant.dart';
|
||||
|
||||
// login
|
||||
class CustomTextFieldLogin extends StatelessWidget {
|
||||
final String hintText;
|
||||
final String labelText;
|
||||
final bool isPassword;
|
||||
final bool obscureText;
|
||||
final bool isMaxLine;
|
||||
final void Function()? onToggle;
|
||||
final TextEditingController? ctrl;
|
||||
final void Function(String)? onChange;
|
||||
final void Function(String)? onSubmitted;
|
||||
final void Function()? onTap;
|
||||
final void Function()? onEditingComplete;
|
||||
final FocusNode? focusNode;
|
||||
final bool isPrefix;
|
||||
|
||||
final bool isError;
|
||||
final bool isTextArea;
|
||||
final bool isReadOnly;
|
||||
|
||||
final bool hasFocus;
|
||||
|
||||
const CustomTextFieldLogin(
|
||||
{Key? key,
|
||||
required this.hintText,
|
||||
required this.labelText,
|
||||
this.isPassword = false,
|
||||
this.isMaxLine = false,
|
||||
this.onToggle,
|
||||
this.obscureText = false,
|
||||
this.ctrl,
|
||||
this.onChange,
|
||||
this.onSubmitted,
|
||||
this.focusNode,
|
||||
this.isPrefix = false,
|
||||
this.isTextArea = false,
|
||||
this.isError = false,
|
||||
this.isReadOnly = false,
|
||||
this.hasFocus = false,
|
||||
this.onTap,
|
||||
this.onEditingComplete})
|
||||
: super(key: key);
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return TextField(
|
||||
autofocus: false,
|
||||
showCursor: (hasFocus) ? true : false,
|
||||
readOnly: isReadOnly,
|
||||
controller: ctrl,
|
||||
enableInteractiveSelection: false,
|
||||
style:
|
||||
Constant.body1(context: context).copyWith(color: Constant.textBlack),
|
||||
obscureText: obscureText,
|
||||
onChanged: onChange,
|
||||
onSubmitted: onSubmitted,
|
||||
onTap: onTap,
|
||||
onEditingComplete: onEditingComplete,
|
||||
focusNode: focusNode,
|
||||
maxLines: (isTextArea) ? 4 : 1,
|
||||
cursorColor: Constant.primaryBlue,
|
||||
decoration: InputDecoration(
|
||||
// fillColor: (hasFocus) ? Constant.primaryMain : Constant.textGrey,
|
||||
filled: true,
|
||||
focusedBorder: OutlineInputBorder(
|
||||
borderSide: BorderSide(
|
||||
color: (hasFocus) ? Constant.primaryMain : Constant.textGrey,
|
||||
width: 2),
|
||||
borderRadius: BorderRadius.circular(8),
|
||||
),
|
||||
enabledBorder: (hasFocus)
|
||||
? OutlineInputBorder(
|
||||
// ignore: prefer_const_constructors
|
||||
borderRadius: BorderRadius.all(Radius.circular(8)),
|
||||
borderSide: BorderSide(
|
||||
color: Constant.primaryMain,
|
||||
width: 1,
|
||||
),
|
||||
)
|
||||
: OutlineInputBorder(
|
||||
// ignore: prefer_const_constructors
|
||||
borderRadius: BorderRadius.all(Radius.circular(8)),
|
||||
borderSide: BorderSide(
|
||||
color: Constant.textGrey,
|
||||
width: 2,
|
||||
),
|
||||
),
|
||||
// hintStyle: Constant.body1_400(context: context)
|
||||
// .copyWith(color: Constant.textBlack),
|
||||
// labelStyle: Constant.body3_400(context: context),
|
||||
hintStyle: Constant.body1(context: context).copyWith(
|
||||
color: (hasFocus) ? Constant.primaryMain : Constant.textGrey),
|
||||
// mainkan focus
|
||||
labelStyle: Constant.body1(context: context).copyWith(
|
||||
color: (hasFocus) ? Constant.primaryMain : Constant.textGrey),
|
||||
labelText: labelText,
|
||||
hintText: hintText,
|
||||
alignLabelWithHint: true,
|
||||
border: OutlineInputBorder(
|
||||
borderRadius: BorderRadius.circular(30),
|
||||
),
|
||||
prefixIcon: isPrefix ? const Icon(Icons.search) : null,
|
||||
prefixStyle: isPrefix ? Constant.body1(context: context) : null,
|
||||
suffixIcon: isPassword
|
||||
? IconButton(
|
||||
alignment: Alignment.centerRight,
|
||||
onPressed: onToggle,
|
||||
icon: Icon(
|
||||
Icons.remove_red_eye,
|
||||
color: (hasFocus) ? Constant.primaryMain : Constant.textGrey,
|
||||
),
|
||||
iconSize: Constant.getActualY(context: context, y: 24),
|
||||
)
|
||||
: null,
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
// selain inputan login
|
||||
class CustomTextFieldInputan extends StatelessWidget {
|
||||
final String hintText;
|
||||
final String labelText;
|
||||
final bool isPassword;
|
||||
final bool obscureText;
|
||||
final bool isMaxLine;
|
||||
final void Function()? onToggle;
|
||||
final TextEditingController? ctrl;
|
||||
final void Function(String)? onChange;
|
||||
final void Function(String)? onSubmitted;
|
||||
final void Function()? onTap;
|
||||
final void Function()? onEditingComplete;
|
||||
final FocusNode? focusNode;
|
||||
final bool isPrefix;
|
||||
|
||||
final bool isError;
|
||||
final bool isTextArea;
|
||||
final bool isReadOnly;
|
||||
|
||||
final bool hasFocus;
|
||||
|
||||
const CustomTextFieldInputan(
|
||||
{Key? key,
|
||||
required this.hintText,
|
||||
required this.labelText,
|
||||
this.isPassword = false,
|
||||
this.isMaxLine = false,
|
||||
this.onToggle,
|
||||
this.obscureText = false,
|
||||
this.ctrl,
|
||||
this.onChange,
|
||||
this.onSubmitted,
|
||||
this.focusNode,
|
||||
this.isPrefix = false,
|
||||
this.isTextArea = false,
|
||||
this.isError = false,
|
||||
this.isReadOnly = false,
|
||||
this.hasFocus = true,
|
||||
this.onTap,
|
||||
this.onEditingComplete})
|
||||
: super(key: key);
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return TextField(
|
||||
enabled: (isReadOnly == true) ? false : true,
|
||||
autofocus: false,
|
||||
showCursor: (hasFocus) ? true : false,
|
||||
readOnly: (isReadOnly == true) ? true : false,
|
||||
controller: ctrl,
|
||||
enableInteractiveSelection: false,
|
||||
style:
|
||||
Constant.body1(context: context).copyWith(color: Constant.textBlack),
|
||||
obscureText: obscureText,
|
||||
onChanged: onChange,
|
||||
onSubmitted: onSubmitted,
|
||||
onTap: (isReadOnly == true) ? null : onTap,
|
||||
onEditingComplete: onEditingComplete,
|
||||
focusNode: focusNode,
|
||||
maxLines: (isTextArea) ? 4 : 1,
|
||||
cursorColor: Constant.primaryBlue,
|
||||
decoration: InputDecoration(
|
||||
// fillColor: (hasFocus) ? Constant.primaryMain : Constant.textGrey,
|
||||
// filled: true,
|
||||
disabledBorder: OutlineInputBorder(
|
||||
// ignore: prefer_const_constructors
|
||||
borderRadius: BorderRadius.all(Radius.circular(8)),
|
||||
borderSide: BorderSide(
|
||||
color: Constant.textGrey,
|
||||
width: 1,
|
||||
),
|
||||
),
|
||||
focusedBorder: OutlineInputBorder(
|
||||
borderSide: BorderSide(color: Constant.primaryMain, width: 2),
|
||||
borderRadius: BorderRadius.circular(8),
|
||||
),
|
||||
enabledBorder: (hasFocus)
|
||||
? OutlineInputBorder(
|
||||
// ignore: prefer_const_constructors
|
||||
borderRadius: BorderRadius.all(Radius.circular(8)),
|
||||
borderSide: BorderSide(
|
||||
color: Constant.primaryMain,
|
||||
width: 1,
|
||||
),
|
||||
)
|
||||
: OutlineInputBorder(
|
||||
// ignore: prefer_const_constructors
|
||||
borderRadius: BorderRadius.all(Radius.circular(8)),
|
||||
borderSide: BorderSide(
|
||||
color: Constant.textGrey,
|
||||
width: 1,
|
||||
),
|
||||
),
|
||||
// hintStyle: Constant.body1_400(context: context)
|
||||
// .copyWith(color: Constant.textBlack),
|
||||
// labelStyle: Constant.body3_400(context: context),
|
||||
hintStyle: Constant.body1(context: context).copyWith(
|
||||
color: (hasFocus) ? Constant.primaryMain : Constant.textGrey),
|
||||
// mainkan focus
|
||||
labelStyle: Constant.body1(context: context).copyWith(
|
||||
color: (hasFocus) ? Constant.primaryMain : Constant.textGrey),
|
||||
labelText: labelText,
|
||||
hintText: hintText,
|
||||
alignLabelWithHint: true,
|
||||
border: OutlineInputBorder(
|
||||
borderRadius: BorderRadius.circular(30),
|
||||
),
|
||||
prefixIcon: isPrefix ? const Icon(Icons.document_scanner) : null,
|
||||
prefixStyle: isPrefix ? Constant.body1(context: context) : null,
|
||||
suffixIcon: isPassword
|
||||
? IconButton(
|
||||
alignment: Alignment.centerRight,
|
||||
onPressed: onToggle,
|
||||
icon: Icon(
|
||||
Icons.remove_red_eye,
|
||||
color: (hasFocus) ? Constant.primaryMain : Constant.textGrey,
|
||||
),
|
||||
iconSize: Constant.getActualY(context: context, y: 24),
|
||||
)
|
||||
: null,
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
23
lib/widget/header_widget.dart
Normal file
23
lib/widget/header_widget.dart
Normal file
@@ -0,0 +1,23 @@
|
||||
import 'package:flutter/material.dart';
|
||||
|
||||
import '../../app/constant.dart';
|
||||
|
||||
class HeaderWidget extends StatelessWidget {
|
||||
const HeaderWidget({super.key, required this.teks});
|
||||
final String teks;
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Container(
|
||||
color: Colors.white,
|
||||
height: Constant.getActualY(context: context, y: 60),
|
||||
width: double.infinity,
|
||||
alignment: Alignment.center,
|
||||
child: Text(
|
||||
teks,
|
||||
style: Constant.heading3(context: context)
|
||||
.copyWith(fontWeight: FontWeight.w600, color: Constant.primaryBlue),
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
143
lib/widget/information_card.dart
Normal file
143
lib/widget/information_card.dart
Normal file
@@ -0,0 +1,143 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:loading_animation_widget/loading_animation_widget.dart';
|
||||
|
||||
import '../../app/constant.dart';
|
||||
import '../../models/work_total_model.dart';
|
||||
|
||||
class InformationCard extends StatelessWidget {
|
||||
const InformationCard(
|
||||
{super.key,
|
||||
this.bgColor,
|
||||
this.elevation = false,
|
||||
required this.data,
|
||||
required this.loading});
|
||||
final Color? bgColor;
|
||||
final bool? elevation;
|
||||
final bool loading;
|
||||
final WorkTotalModel data;
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Container(
|
||||
decoration: BoxDecoration(
|
||||
borderRadius: BorderRadius.circular(40),
|
||||
color: bgColor ?? Colors.white,
|
||||
// border: Border.all(width: 0),
|
||||
boxShadow: [
|
||||
if (elevation == true)
|
||||
BoxShadow(
|
||||
color: Colors.grey.shade200,
|
||||
offset: Offset(0.0, 1.0), //(x,y)
|
||||
blurRadius: 2,
|
||||
),
|
||||
if (elevation == false)
|
||||
BoxShadow(
|
||||
color: Color(0XFF0000000F).withOpacity(0.06),
|
||||
offset: Offset(0.0, 2), //(x,y)
|
||||
blurRadius: 30,
|
||||
),
|
||||
],
|
||||
),
|
||||
height: Constant.getActualY(context: context, y: 112),
|
||||
padding: EdgeInsets.symmetric(
|
||||
horizontal: Constant.getActualX(context: context, x: 32),
|
||||
vertical: Constant.getActualY(context: context, y: 12)),
|
||||
child: SizedBox(
|
||||
// color: Colors.blue,
|
||||
height: Constant.getActualY(context: context, y: 88),
|
||||
child: Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceAround,
|
||||
children: [
|
||||
Column(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
|
||||
children: [
|
||||
Image.asset(
|
||||
width: Constant.getActualX(context: context, x: 24),
|
||||
height: Constant.getActualX(context: context, x: 24),
|
||||
"assets/icon_home_total_yellow.png"),
|
||||
loading
|
||||
? SizedBox(
|
||||
height: Constant.getActualX(context: context, x: 20),
|
||||
width: Constant.getActualX(context: context, x: 20),
|
||||
child: LoadingAnimationWidget.discreteCircle(
|
||||
color: Constant.primaryBlue, size: 20))
|
||||
: Text(
|
||||
"${data.totalAll}",
|
||||
textAlign: TextAlign.center,
|
||||
overflow: TextOverflow.ellipsis,
|
||||
style: Constant.body3(context: context)
|
||||
.copyWith(fontWeight: FontWeight.w600),
|
||||
),
|
||||
Text(
|
||||
"Total",
|
||||
overflow: TextOverflow.ellipsis,
|
||||
style: Constant.body3(context: context).copyWith(
|
||||
fontWeight: FontWeight.w600,
|
||||
color: Constant.textSecondary),
|
||||
)
|
||||
],
|
||||
),
|
||||
Column(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceAround,
|
||||
children: [
|
||||
Image.asset(
|
||||
"assets/icon_home_diterima_yellow.png",
|
||||
width: Constant.getActualX(context: context, x: 24),
|
||||
height: Constant.getActualX(context: context, x: 24),
|
||||
),
|
||||
loading
|
||||
? SizedBox(
|
||||
height: Constant.getActualX(context: context, x: 20),
|
||||
width: Constant.getActualX(context: context, x: 20),
|
||||
child: LoadingAnimationWidget.discreteCircle(
|
||||
color: Constant.primaryBlue, size: 20))
|
||||
: Text(
|
||||
"${data.receive}",
|
||||
overflow: TextOverflow.ellipsis,
|
||||
style: Constant.body3(context: context).copyWith(
|
||||
fontWeight: FontWeight.w600,
|
||||
),
|
||||
),
|
||||
Text(
|
||||
"Diterima",
|
||||
overflow: TextOverflow.ellipsis,
|
||||
style: Constant.body3(context: context).copyWith(
|
||||
fontWeight: FontWeight.w600,
|
||||
color: Constant.textSecondary),
|
||||
)
|
||||
],
|
||||
),
|
||||
Column(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceAround,
|
||||
children: [
|
||||
Image.asset(
|
||||
width: Constant.getActualX(context: context, x: 24),
|
||||
height: Constant.getActualX(context: context, x: 24),
|
||||
"assets/icon_home_selesai_yellow.png"),
|
||||
loading
|
||||
? SizedBox(
|
||||
height: Constant.getActualX(context: context, x: 20),
|
||||
width: Constant.getActualX(context: context, x: 20),
|
||||
child: LoadingAnimationWidget.discreteCircle(
|
||||
color: Constant.primaryBlue, size: 20))
|
||||
: Text(
|
||||
"${data.done}",
|
||||
overflow: TextOverflow.ellipsis,
|
||||
style: Constant.body3(context: context).copyWith(
|
||||
fontWeight: FontWeight.w600,
|
||||
),
|
||||
),
|
||||
Text(
|
||||
"Selesai",
|
||||
overflow: TextOverflow.ellipsis,
|
||||
style: Constant.body3(context: context).copyWith(
|
||||
fontWeight: FontWeight.w600,
|
||||
color: Constant.textSecondary),
|
||||
)
|
||||
],
|
||||
)
|
||||
],
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
89
lib/widget/information_rpt_card.dart
Normal file
89
lib/widget/information_rpt_card.dart
Normal file
@@ -0,0 +1,89 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:hooks_riverpod/hooks_riverpod.dart';
|
||||
import '/app/constant.dart';
|
||||
import '/widget/open_pdf_widget.dart';
|
||||
import '/widget/rpt_date.dart';
|
||||
import 'package:url_launcher/url_launcher.dart';
|
||||
|
||||
class InformationRptCard extends HookConsumerWidget {
|
||||
final String courierID;
|
||||
const InformationRptCard(this.courierID, {super.key});
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context, WidgetRef ref) {
|
||||
// final Uri url = Uri.parse("http://devone.aplikasi.web.id/");
|
||||
// final Uri url = Uri.parse("https://www.google.com/");
|
||||
final Uri url = Uri.parse(
|
||||
"${Constant.baseBirtUrl}app-birt/run?__report=report/one/rekap/rpt_total_order_kurir.rptdesign&__format=pdf&courierID=40");
|
||||
Future<void> _launchUrl() async {
|
||||
print(url);
|
||||
if (!await launchUrl(url)) {
|
||||
throw Exception('Could not launch $url');
|
||||
}
|
||||
}
|
||||
|
||||
return Container(
|
||||
// padding: EdgeInsets.fromLTRB(
|
||||
// Constant.getActualY(context: context, y: 30),
|
||||
// Constant.getActualX(context: context, x: 24),
|
||||
// Constant.getActualX(context: context, x: 10),
|
||||
// Constant.getActualY(context: context, y: 30)),
|
||||
height: Constant.getActualY(context: context, y: 180),
|
||||
decoration: BoxDecoration(
|
||||
image: DecorationImage(image: AssetImage("assets/kurir_bg_card.png")),
|
||||
borderRadius: BorderRadius.circular(20)),
|
||||
child: Row(
|
||||
children: [
|
||||
Expanded(
|
||||
flex: 5,
|
||||
child: Padding(
|
||||
padding: EdgeInsets.fromLTRB(
|
||||
Constant.getActualY(context: context, y: 30),
|
||||
Constant.getActualX(context: context, x: 24),
|
||||
0,
|
||||
Constant.getActualY(context: context, y: 30)),
|
||||
child: Column(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceAround,
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Text(
|
||||
"Status Total Pekerjaan",
|
||||
style: Constant.body1(context: context).copyWith(
|
||||
fontWeight: FontWeight.w700, color: Colors.white),
|
||||
),
|
||||
ElevatedButton(
|
||||
onPressed: () {
|
||||
// Navigator.push(
|
||||
// context,
|
||||
// MaterialPageRoute(
|
||||
// builder: (context) =>
|
||||
// PdfViewerPage(courierID: courierID),
|
||||
// ));
|
||||
|
||||
// _launchUrl();
|
||||
RptDate(context, ref, courierID);
|
||||
},
|
||||
child: Text(
|
||||
"Lihat RPT",
|
||||
style: Constant.caption1(context: context).copyWith(
|
||||
fontWeight: FontWeight.w700,
|
||||
color: Color(0xff3366FF)),
|
||||
),
|
||||
style: ElevatedButton.styleFrom(
|
||||
shape: RoundedRectangleBorder(
|
||||
borderRadius: BorderRadius.circular(12)),
|
||||
elevation: 0,
|
||||
backgroundColor: Colors.white)),
|
||||
],
|
||||
),
|
||||
)),
|
||||
Expanded(
|
||||
flex: 7,
|
||||
child: Container(
|
||||
// color: Colors.red,
|
||||
child: Image.asset("assets/kurir_icon_card.png")))
|
||||
],
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
339
lib/widget/konfirmasi_kurir_dialog.dart
Normal file
339
lib/widget/konfirmasi_kurir_dialog.dart
Normal file
@@ -0,0 +1,339 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_hooks/flutter_hooks.dart';
|
||||
import '/widget/chip_type.dart';
|
||||
|
||||
import '../app/constant.dart';
|
||||
|
||||
showConfirmCourierDialog(
|
||||
{required BuildContext context,
|
||||
required int tipeid,
|
||||
required String tipe,
|
||||
required String tipee,
|
||||
required String tujuann,
|
||||
required String penerimaa,
|
||||
required TextEditingController noteKurir,
|
||||
required VoidCallback okCallback}) {
|
||||
return showDialog(
|
||||
context: context,
|
||||
builder: (BuildContext context) {
|
||||
return AlertDialog(
|
||||
insetPadding: EdgeInsets.symmetric(
|
||||
horizontal: Constant.getActualX(context: context, x: 35),
|
||||
),
|
||||
title: const Text(
|
||||
"Konfirmasi Pekerjaan",
|
||||
style: TextStyle(fontWeight: FontWeight.bold),
|
||||
),
|
||||
content: tipe == "Tolak"
|
||||
? TolakDialog(
|
||||
tipeid: tipeid,
|
||||
tipee: tipee,
|
||||
tujuann: tujuann,
|
||||
penerimaa: penerimaa,
|
||||
noteKurir: noteKurir,
|
||||
)
|
||||
: TerimaDialog(
|
||||
tipeid: tipeid,
|
||||
tipee: tipee,
|
||||
tujuann: tujuann,
|
||||
penerimaa: penerimaa),
|
||||
actions: [
|
||||
Container(
|
||||
padding: EdgeInsets.symmetric(
|
||||
horizontal: Constant.getActualX(context: context, x: 15),
|
||||
vertical: Constant.getActualY(context: context, y: 8)),
|
||||
child: Column(
|
||||
children: [
|
||||
Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
children: [
|
||||
OutlinedButton(
|
||||
onPressed: () => Navigator.pop(context, 'Cancel'),
|
||||
style: OutlinedButton.styleFrom(
|
||||
side: BorderSide(
|
||||
style: BorderStyle.solid,
|
||||
color: Constant.textGrey),
|
||||
shape: RoundedRectangleBorder(
|
||||
side: BorderSide(
|
||||
style: BorderStyle.solid,
|
||||
color: Constant.textPrimary),
|
||||
borderRadius: BorderRadius.circular(8),
|
||||
),
|
||||
),
|
||||
child: const Text(
|
||||
"Batal",
|
||||
style: TextStyle(
|
||||
fontWeight: FontWeight.bold,
|
||||
color: Colors.black),
|
||||
)),
|
||||
tipe == "Tolak"
|
||||
? ElevatedButton(
|
||||
onPressed: () {
|
||||
okCallback();
|
||||
Navigator.of(context).pop();
|
||||
},
|
||||
// onPressed: {} () => Navigator.pop(context, 'OK'),
|
||||
style: ElevatedButton.styleFrom(
|
||||
backgroundColor: Colors.red,
|
||||
shape: RoundedRectangleBorder(
|
||||
borderRadius: BorderRadius.circular(8),
|
||||
),
|
||||
),
|
||||
child: const Text(
|
||||
"Tolak",
|
||||
style: TextStyle(fontWeight: FontWeight.bold),
|
||||
),
|
||||
)
|
||||
: ElevatedButton(
|
||||
onPressed: () {
|
||||
okCallback();
|
||||
Navigator.pop(context);
|
||||
},
|
||||
style: ElevatedButton.styleFrom(
|
||||
shape: RoundedRectangleBorder(
|
||||
borderRadius: BorderRadius.circular(8),
|
||||
),
|
||||
),
|
||||
child: const Text(
|
||||
"Terima",
|
||||
style: TextStyle(fontWeight: FontWeight.bold),
|
||||
),
|
||||
),
|
||||
]),
|
||||
],
|
||||
),
|
||||
)
|
||||
],
|
||||
shape: RoundedRectangleBorder(
|
||||
side: BorderSide(
|
||||
color: Theme.of(context).colorScheme.outline,
|
||||
),
|
||||
borderRadius: const BorderRadius.all(Radius.circular(12)),
|
||||
),
|
||||
);
|
||||
});
|
||||
}
|
||||
|
||||
class TerimaDialog extends StatelessWidget {
|
||||
const TerimaDialog({
|
||||
super.key,
|
||||
required this.tipeid,
|
||||
required this.tipee,
|
||||
required this.tujuann,
|
||||
required this.penerimaa,
|
||||
});
|
||||
final int tipeid;
|
||||
final String tipee;
|
||||
final String tujuann;
|
||||
final String penerimaa;
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Container(
|
||||
child: SingleChildScrollView(
|
||||
child: Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
Text(
|
||||
"Anda menerima pekerjaan ini ?",
|
||||
style: Constant.body2(context: context).copyWith(
|
||||
fontWeight: FontWeight.w400, color: Constant.textPrimary),
|
||||
),
|
||||
Container(
|
||||
margin: const EdgeInsets.fromLTRB(0, 16, 0, 0),
|
||||
width: double.infinity,
|
||||
child: Card(
|
||||
elevation: 2,
|
||||
shape: RoundedRectangleBorder(
|
||||
side: BorderSide(
|
||||
color: Theme.of(context).colorScheme.outline,
|
||||
),
|
||||
borderRadius: const BorderRadius.all(Radius.circular(12)),
|
||||
),
|
||||
child: Container(
|
||||
padding: const EdgeInsets.all(16),
|
||||
child: Column(
|
||||
children: [
|
||||
Row(
|
||||
mainAxisAlignment: MainAxisAlignment.start,
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Expanded(
|
||||
flex: 3,
|
||||
child: Text("Tipe",
|
||||
style: Constant.caption1(context: context))),
|
||||
Expanded(
|
||||
flex: 5,
|
||||
child: ChipType(
|
||||
tipe: tipeid,
|
||||
name: tipee,
|
||||
isDetailHistory: false,
|
||||
),
|
||||
)
|
||||
],
|
||||
),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
Row(
|
||||
mainAxisAlignment: MainAxisAlignment.start,
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Expanded(
|
||||
flex: 3,
|
||||
child: Text("Tujuan",
|
||||
style: Constant.caption1(context: context))),
|
||||
Expanded(
|
||||
flex: 5,
|
||||
child: Text(tujuann,
|
||||
style: TextStyle(
|
||||
color: Constant.textGrey, fontSize: 12)))
|
||||
],
|
||||
),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
Row(
|
||||
mainAxisAlignment: MainAxisAlignment.start,
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Expanded(
|
||||
flex: 3,
|
||||
child: Text("Penerima",
|
||||
style: Constant.caption1(context: context))),
|
||||
Expanded(
|
||||
flex: 5,
|
||||
child: Text(penerimaa,
|
||||
style: TextStyle(
|
||||
color: Constant.textGrey, fontSize: 12)))
|
||||
],
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class TolakDialog extends StatelessWidget {
|
||||
const TolakDialog({
|
||||
super.key,
|
||||
required this.tipeid,
|
||||
required this.tipee,
|
||||
required this.tujuann,
|
||||
required this.penerimaa,
|
||||
required this.noteKurir,
|
||||
});
|
||||
final int tipeid;
|
||||
final String tipee;
|
||||
final String tujuann;
|
||||
final String penerimaa;
|
||||
final TextEditingController noteKurir;
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Container(
|
||||
child: SingleChildScrollView(
|
||||
child: Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
Text(
|
||||
"Anda menolak pekerjaan ini ?",
|
||||
style: Constant.body2(context: context).copyWith(
|
||||
fontWeight: FontWeight.w400, color: Constant.textPrimary),
|
||||
),
|
||||
Container(
|
||||
margin: const EdgeInsets.fromLTRB(0, 16, 0, 25),
|
||||
width: double.infinity,
|
||||
child: Card(
|
||||
elevation: 2,
|
||||
shape: RoundedRectangleBorder(
|
||||
side: BorderSide(
|
||||
color: Theme.of(context).colorScheme.outline,
|
||||
),
|
||||
borderRadius: const BorderRadius.all(Radius.circular(12)),
|
||||
),
|
||||
child: Container(
|
||||
padding: const EdgeInsets.all(16),
|
||||
child: Column(
|
||||
children: [
|
||||
Row(
|
||||
mainAxisAlignment: MainAxisAlignment.start,
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Expanded(
|
||||
flex: 3,
|
||||
child: Text("Tipe",
|
||||
style: Constant.caption1(context: context))),
|
||||
Expanded(
|
||||
flex: 5,
|
||||
child: ChipType(
|
||||
tipe: tipeid,
|
||||
name: tipee,
|
||||
isDetailHistory: false,
|
||||
),
|
||||
)
|
||||
],
|
||||
),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
Row(
|
||||
mainAxisAlignment: MainAxisAlignment.start,
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Expanded(
|
||||
flex: 3,
|
||||
child: Text("Tujuan",
|
||||
style: Constant.caption1(context: context))),
|
||||
Expanded(
|
||||
flex: 5,
|
||||
child: Text(tujuann,
|
||||
style: TextStyle(
|
||||
color: Constant.textGrey, fontSize: 12)))
|
||||
],
|
||||
),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
Row(
|
||||
mainAxisAlignment: MainAxisAlignment.start,
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Expanded(
|
||||
flex: 3,
|
||||
child: Text("Penerima",
|
||||
style: Constant.caption1(context: context))),
|
||||
Expanded(
|
||||
flex: 5,
|
||||
child: Text(penerimaa,
|
||||
style: TextStyle(
|
||||
color: Constant.textGrey, fontSize: 12)))
|
||||
],
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
TextField(
|
||||
controller: noteKurir,
|
||||
maxLines: 1,
|
||||
decoration: const InputDecoration(
|
||||
labelStyle: TextStyle(color: Colors.grey),
|
||||
border: OutlineInputBorder(
|
||||
borderSide: BorderSide(color: Colors.grey),
|
||||
borderRadius: BorderRadius.all(Radius.circular(12))),
|
||||
labelText: 'Alasan',
|
||||
),
|
||||
)
|
||||
],
|
||||
),
|
||||
));
|
||||
}
|
||||
}
|
||||
127
lib/widget/map_dialog.dart
Normal file
127
lib/widget/map_dialog.dart
Normal file
@@ -0,0 +1,127 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_map/flutter_map.dart';
|
||||
import 'package:latlong2/latlong.dart';
|
||||
|
||||
import '../app/constant.dart';
|
||||
|
||||
typedef void MyFunction();
|
||||
|
||||
showMapDialog({
|
||||
required BuildContext context,
|
||||
required double lat,
|
||||
required double long,
|
||||
required MyFunction confirm,
|
||||
required MyFunction notConfirm,
|
||||
required String address,
|
||||
}) {
|
||||
return showDialog(
|
||||
context: context,
|
||||
builder: (BuildContext context) {
|
||||
return AlertDialog(
|
||||
title: Text(
|
||||
"Konfirmasi lokasi",
|
||||
style: Constant.body1(context: context),
|
||||
),
|
||||
content: SizedBox(
|
||||
width: Constant.getActualX(context: context, x: 280),
|
||||
height: Constant.getActualY(context: context, y: 200),
|
||||
child: SizedBox(
|
||||
width: Constant.getActualX(context: context, x: 200),
|
||||
height: Constant.getActualY(context: context, y: 100),
|
||||
// child: FlutterMap(
|
||||
// options: MapOptions(
|
||||
// center: LatLng(lat, long),
|
||||
// zoom: 16,
|
||||
// ),
|
||||
// nonRotatedChildren: [
|
||||
// Align(
|
||||
// alignment: Alignment.bottomLeft,
|
||||
// child: Text(
|
||||
// address,
|
||||
// style: Constant.body1(context: context).copyWith(
|
||||
// backgroundColor: Colors.black.withOpacity(0.5),
|
||||
// color: Colors.white),
|
||||
// ),
|
||||
// ),
|
||||
// ],
|
||||
// children: [
|
||||
// TileLayer(
|
||||
// urlTemplate: 'https://tile.openstreetmap.org/{z}/{x}/{y}.png',
|
||||
// userAgentPackageName: 'com.example.app',
|
||||
// ),
|
||||
// MarkerLayer(
|
||||
// markers: [
|
||||
// Marker(
|
||||
// point: LatLng(lat, long),
|
||||
// width: 100,
|
||||
// height: 100,
|
||||
// builder: (context) => const Icon(
|
||||
// Icons.location_on,
|
||||
// color: Colors.red,
|
||||
// size: 50,
|
||||
// )),
|
||||
// ],
|
||||
// ),
|
||||
// ],
|
||||
// ),
|
||||
child: FlutterMap(
|
||||
options: MapOptions(
|
||||
initialCenter: LatLng(lat, long),
|
||||
initialZoom: 16,
|
||||
),
|
||||
children: [
|
||||
TileLayer(
|
||||
urlTemplate: 'https://tile.openstreetmap.org/{z}/{x}/{y}.png',
|
||||
userAgentPackageName: 'com.example.app',
|
||||
),
|
||||
MarkerLayer(
|
||||
markers: [
|
||||
Marker(
|
||||
point: LatLng(lat, long),
|
||||
width: 100,
|
||||
height: 100,
|
||||
child: const Icon(
|
||||
Icons.location_on,
|
||||
color: Colors.red,
|
||||
size: 50,
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
Align(
|
||||
alignment: Alignment.bottomLeft,
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.all(8.0),
|
||||
child: Text(
|
||||
address,
|
||||
style: Constant.body1(context: context).copyWith(
|
||||
// backgroundColor: Colors.black.withOpacity(0.5),
|
||||
backgroundColor: Colors.black.withAlpha(128),
|
||||
color: Colors.white,
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
actions: [
|
||||
OutlinedButton(
|
||||
onPressed: () {
|
||||
Navigator.pop(context);
|
||||
notConfirm();
|
||||
},
|
||||
child: const Text("Ulangi"),
|
||||
),
|
||||
SizedBox(width: Constant.getActualX(context: context, x: 5)),
|
||||
ElevatedButton(onPressed: confirm, child: Text("ya")),
|
||||
SizedBox(width: Constant.getActualX(context: context, x: 10)),
|
||||
],
|
||||
shape: const RoundedRectangleBorder(
|
||||
borderRadius: BorderRadius.all(Radius.circular(24)),
|
||||
),
|
||||
);
|
||||
},
|
||||
);
|
||||
}
|
||||
81
lib/widget/open_pdf_widget.dart
Normal file
81
lib/widget/open_pdf_widget.dart
Normal file
@@ -0,0 +1,81 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_pdfview/flutter_pdfview.dart';
|
||||
import 'dart:io';
|
||||
import 'package:http/http.dart' as http;
|
||||
import 'package:intl/intl.dart';
|
||||
import '/widget/snackbar_widget.dart';
|
||||
import 'package:path/path.dart';
|
||||
import 'package:path_provider/path_provider.dart';
|
||||
|
||||
import '../app/constant.dart';
|
||||
|
||||
class PdfViewerPage extends StatefulWidget {
|
||||
final String courierID;
|
||||
final String date;
|
||||
|
||||
const PdfViewerPage({super.key, required this.courierID, required this.date});
|
||||
@override
|
||||
_PdfViewerPageState createState() => _PdfViewerPageState();
|
||||
}
|
||||
|
||||
class _PdfViewerPageState extends State<PdfViewerPage> {
|
||||
// final crr = widget.courierID;
|
||||
late File Pfile;
|
||||
bool isLoading = false;
|
||||
|
||||
Future<void> loadNetwork() async {
|
||||
try {
|
||||
setState(() {
|
||||
isLoading = true;
|
||||
});
|
||||
// http: //10.9.9.3/birt/run?__report=report/one/rekap/rpt_total_order_kurir.rptdesign&__format=pdf&courierID=44&date=2023-09-07
|
||||
var url =
|
||||
"${Constant.baseBirtUrl}app-birt/run?__report=report/one/rekap/rpt_total_order_kurir.rptdesign&__format=pdf&courierID=${widget.courierID}&date=${widget.date}";
|
||||
final response = await http.get(Uri.parse(url));
|
||||
print(url);
|
||||
final bytes = response.bodyBytes;
|
||||
final filename = basename(url);
|
||||
final dir = await getApplicationDocumentsDirectory();
|
||||
var file = File('${dir.path}/$filename');
|
||||
await file.writeAsBytes(bytes, flush: true);
|
||||
setState(() {
|
||||
Pfile = file;
|
||||
});
|
||||
|
||||
print(Pfile);
|
||||
setState(() {
|
||||
isLoading = false;
|
||||
});
|
||||
} catch (e) {
|
||||
print(e);
|
||||
}
|
||||
}
|
||||
|
||||
@override
|
||||
void initState() {
|
||||
loadNetwork();
|
||||
|
||||
super.initState();
|
||||
}
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Scaffold(
|
||||
appBar: AppBar(
|
||||
title: Text(
|
||||
"${widget.date}",
|
||||
style: TextStyle(fontWeight: FontWeight.bold),
|
||||
),
|
||||
),
|
||||
body: isLoading
|
||||
? Center(child: CircularProgressIndicator())
|
||||
: Container(
|
||||
child: Center(
|
||||
child: PDFView(
|
||||
filePath: Pfile.path,
|
||||
),
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
130
lib/widget/patient_card.dart
Normal file
130
lib/widget/patient_card.dart
Normal file
@@ -0,0 +1,130 @@
|
||||
import 'package:flutter/material.dart';
|
||||
|
||||
import '../app/constant.dart';
|
||||
|
||||
typedef void MyFunction();
|
||||
|
||||
class PatientCard extends StatelessWidget {
|
||||
const PatientCard({
|
||||
super.key,
|
||||
required this.name,
|
||||
required this.noLab,
|
||||
this.note,
|
||||
this.onClick,
|
||||
});
|
||||
final String name;
|
||||
final String noLab;
|
||||
final String? note;
|
||||
final MyFunction? onClick;
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return InkWell(
|
||||
onTap: onClick,
|
||||
child: Container(
|
||||
padding: EdgeInsets.symmetric(
|
||||
horizontal: Constant.getActualX(context: context, x: 24),
|
||||
vertical: Constant.getActualY(context: context, y: 20)),
|
||||
margin: EdgeInsets.symmetric(
|
||||
vertical: Constant.getActualY(context: context, y: 4),
|
||||
horizontal: Constant.getActualX(context: context, x: 1)),
|
||||
// height: Constant.getActualY(context: context, y: 76),
|
||||
decoration: BoxDecoration(
|
||||
color: Colors.white,
|
||||
border: Border.all(color: Colors.grey, width: 0.1),
|
||||
boxShadow: [
|
||||
BoxShadow(
|
||||
color: Colors.grey.shade300,
|
||||
offset: const Offset(0.0, 1), //(x,y)
|
||||
blurRadius: 2,
|
||||
),
|
||||
],
|
||||
borderRadius: BorderRadius.circular(12)),
|
||||
child: Column(
|
||||
children: [
|
||||
Row(
|
||||
mainAxisAlignment: MainAxisAlignment.start,
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Expanded(
|
||||
child: Text(
|
||||
"Nomor lab",
|
||||
style: Constant.caption1(context: context).copyWith(
|
||||
fontWeight: FontWeight.w400,
|
||||
color: Constant.textPrimary),
|
||||
),
|
||||
),
|
||||
Expanded(
|
||||
child: Text(
|
||||
noLab,
|
||||
maxLines: 2,
|
||||
overflow: TextOverflow.ellipsis,
|
||||
style: Constant.caption1(context: context).copyWith(
|
||||
fontWeight: FontWeight.w400,
|
||||
color: Constant.textPrimary),
|
||||
),
|
||||
)
|
||||
],
|
||||
),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 4),
|
||||
),
|
||||
Row(
|
||||
mainAxisAlignment: MainAxisAlignment.start,
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Expanded(
|
||||
child: Text(
|
||||
"Nama",
|
||||
style: Constant.caption1(context: context).copyWith(
|
||||
fontWeight: FontWeight.w400,
|
||||
color: Constant.textPrimary),
|
||||
),
|
||||
),
|
||||
Expanded(
|
||||
child: Text(
|
||||
name,
|
||||
maxLines: 2,
|
||||
overflow: TextOverflow.ellipsis,
|
||||
style: Constant.caption1(context: context).copyWith(
|
||||
fontWeight: FontWeight.w400,
|
||||
color: Constant.textPrimary),
|
||||
),
|
||||
)
|
||||
],
|
||||
),
|
||||
if (note != null)
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 4),
|
||||
),
|
||||
if (note != null)
|
||||
Row(
|
||||
mainAxisAlignment: MainAxisAlignment.start,
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Expanded(
|
||||
child: Text(
|
||||
"Catatan FO",
|
||||
style: Constant.caption1(context: context).copyWith(
|
||||
fontWeight: FontWeight.w400,
|
||||
color: Constant.textPrimary),
|
||||
),
|
||||
),
|
||||
Expanded(
|
||||
child: Text(
|
||||
note ?? "",
|
||||
maxLines: 2,
|
||||
overflow: TextOverflow.ellipsis,
|
||||
style: Constant.caption1(context: context).copyWith(
|
||||
fontWeight: FontWeight.w400,
|
||||
color: Constant.textPrimary),
|
||||
),
|
||||
)
|
||||
],
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
282
lib/widget/pending_card.dart
Normal file
282
lib/widget/pending_card.dart
Normal file
@@ -0,0 +1,282 @@
|
||||
import 'package:dotted_line/dotted_line.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:hooks_riverpod/hooks_riverpod.dart';
|
||||
import '../models/work_list_model.dart';
|
||||
import '/screen/work_process_screen/work_process_screen.dart';
|
||||
|
||||
import '../../app/constant.dart';
|
||||
import '../../app/route.dart';
|
||||
import '../../models/pending_work_model.dart';
|
||||
import '../provider/current_user_provider.dart';
|
||||
import 'chip_type.dart';
|
||||
|
||||
class PendingCardWidget extends HookConsumerWidget {
|
||||
const PendingCardWidget({super.key, required this.data});
|
||||
|
||||
final PendingWorkModel data;
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context, WidgetRef ref) {
|
||||
Widget cardValue(String name, String value) {
|
||||
return Row(
|
||||
mainAxisAlignment: MainAxisAlignment.start,
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Expanded(
|
||||
child: Text(
|
||||
name,
|
||||
style: Constant.caption1(context: context).copyWith(
|
||||
fontWeight: FontWeight.w400, color: Constant.textPrimary),
|
||||
),
|
||||
),
|
||||
Text(
|
||||
": ",
|
||||
style: Constant.caption2(context: context).copyWith(
|
||||
fontWeight: FontWeight.w400, color: Constant.textPrimary),
|
||||
),
|
||||
Expanded(
|
||||
child: Text(
|
||||
"${value}",
|
||||
style: Constant.caption1(context: context).copyWith(
|
||||
fontWeight: FontWeight.w400, color: Constant.textPrimary),
|
||||
),
|
||||
),
|
||||
],
|
||||
);
|
||||
}
|
||||
|
||||
return Container(
|
||||
margin: EdgeInsets.symmetric(
|
||||
vertical: Constant.getActualY(context: context, y: 4)),
|
||||
// color: Colors.blue,
|
||||
// height: Constant.getActualY(context: context, y: 170),
|
||||
width: double.infinity,
|
||||
child: Card(
|
||||
shape: RoundedRectangleBorder(borderRadius: BorderRadius.circular(12)),
|
||||
child: Container(
|
||||
decoration: BoxDecoration(
|
||||
color: Colors.white,
|
||||
border: Border.all(color: Colors.grey, width: 0.1),
|
||||
boxShadow: [
|
||||
BoxShadow(
|
||||
color: Color(0XFF919EAB).withOpacity(0.12),
|
||||
offset: Offset(0.0, 12), //(x,y)
|
||||
blurRadius: 24,
|
||||
spreadRadius: -4),
|
||||
BoxShadow(
|
||||
color: Color(0XFF919EAB).withOpacity(0.2),
|
||||
offset: Offset(0.0, 0), //(x,y)
|
||||
blurRadius: 2,
|
||||
),
|
||||
],
|
||||
borderRadius: BorderRadius.circular(12)),
|
||||
child: ElevatedButton(
|
||||
style: ElevatedButton.styleFrom(
|
||||
elevation: 0.2,
|
||||
shape: RoundedRectangleBorder(
|
||||
side: BorderSide(width: 0.1, color: Colors.grey),
|
||||
borderRadius: BorderRadius.circular(12),
|
||||
),
|
||||
backgroundColor: Colors.white,
|
||||
foregroundColor: Colors.grey),
|
||||
onPressed: () {
|
||||
if (data.supervisor == "Dikonfirmasi") {
|
||||
Navigator.pushNamed(
|
||||
context,
|
||||
workProcessRoute,
|
||||
arguments: DetailWorkProp(
|
||||
data.tipeid!,
|
||||
ref.watch(currentUserProvider)?.model.user?.mCourierID ??
|
||||
"0",
|
||||
data.id.toString(),
|
||||
data.noLab.toString(),
|
||||
data.nama.toString(),
|
||||
data.note.toString()),
|
||||
);
|
||||
}
|
||||
},
|
||||
child: Padding(
|
||||
padding: EdgeInsets.symmetric(
|
||||
horizontal: Constant.getActualX(context: context, x: 18),
|
||||
vertical: Constant.getActualY(context: context, y: 20)),
|
||||
child: Column(
|
||||
mainAxisAlignment: MainAxisAlignment.start,
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
children: [
|
||||
ChipType(
|
||||
tipe: data.tipeid!,
|
||||
name: data.tipe!,
|
||||
isDetailHistory: false),
|
||||
if (data.supervisor == "Dikonfirmasi")
|
||||
Icon(
|
||||
Icons.check_circle_outline_rounded,
|
||||
color: Constant.primaryGreen,
|
||||
size: 15,
|
||||
),
|
||||
if (data.supervisor == "Belum dikonfirmasi")
|
||||
Icon(
|
||||
Icons.help_outline_rounded,
|
||||
color: Constant.primaryOrange,
|
||||
size: 15,
|
||||
),
|
||||
if (data.supervisor == "Ditoalk")
|
||||
Icon(
|
||||
Icons.cancel_outlined,
|
||||
color: Constant.primaryRed,
|
||||
size: 15,
|
||||
),
|
||||
],
|
||||
),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 12),
|
||||
),
|
||||
if (data.tipeid == 1)
|
||||
Column(
|
||||
children: [
|
||||
cardValue("Nomot Lab", data.noLab ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Nama", data.nama ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Cabang Pengirim", data.branchname ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Alamat Pengantaran", data.alamat ?? ""),
|
||||
],
|
||||
),
|
||||
if (data.tipeid == 2)
|
||||
Column(
|
||||
children: [
|
||||
cardValue("Nomot Surat Jalan", data.noSuratJalan ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Nama", data.nama ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Cabang Pengirim", data.branchname ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Alamat Pengantaran", data.alamat ?? ""),
|
||||
],
|
||||
),
|
||||
if (data.tipeid == 3)
|
||||
Column(
|
||||
children: [
|
||||
cardValue("Nomot Surat Jalan", data.noSuratJalan ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Nama", data.nama ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Cabang Pengirim", data.branchname ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Alamat Pengantaran", data.alamat ?? ""),
|
||||
],
|
||||
),
|
||||
if (data.tipeid == 4)
|
||||
Column(
|
||||
children: [
|
||||
cardValue("Catatan", data.note ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Pengirim", data.branchaddress ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Penerima", data.alamat ?? ""),
|
||||
],
|
||||
),
|
||||
if (data.tipeid == 5)
|
||||
Column(
|
||||
children: [
|
||||
cardValue("Tujuan", data.nama ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Alamat", data.branchaddress ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Cabang penerima", data.branchname ?? ""),
|
||||
],
|
||||
),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 16),
|
||||
),
|
||||
Row(
|
||||
children: [
|
||||
Icon(
|
||||
Icons.circle_outlined,
|
||||
color: Colors.grey.shade300,
|
||||
size: 15,
|
||||
),
|
||||
SizedBox(
|
||||
width: Constant.getActualX(context: context, x: 12),
|
||||
),
|
||||
Expanded(
|
||||
flex: 5,
|
||||
child: DottedLine(
|
||||
dashColor: Colors.grey.shade300,
|
||||
)),
|
||||
SizedBox(
|
||||
width: Constant.getActualX(context: context, x: 12),
|
||||
),
|
||||
if (data.statusTransaksi == "Baru")
|
||||
Icon(
|
||||
Icons.circle_outlined,
|
||||
color: Constant.primaryBlue,
|
||||
size: 15,
|
||||
),
|
||||
if (data.statusTransaksi == "Proses")
|
||||
Icon(
|
||||
Icons.circle_outlined,
|
||||
color: Constant.primaryYellow,
|
||||
size: 15,
|
||||
),
|
||||
if (data.statusTransaksi == "Done" ||
|
||||
data.statusTransaksi == "Selesai")
|
||||
Icon(
|
||||
Icons.circle_outlined,
|
||||
color: Constant.primaryGreen,
|
||||
size: 15,
|
||||
),
|
||||
SizedBox(
|
||||
width: Constant.getActualX(context: context, x: 4),
|
||||
),
|
||||
Text(
|
||||
"${data.statusTransaksi}",
|
||||
style: Constant.caption2(context: context)
|
||||
.copyWith(color: Constant.textPrimary),
|
||||
),
|
||||
],
|
||||
)
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
117
lib/widget/rpt_date.dart
Normal file
117
lib/widget/rpt_date.dart
Normal file
@@ -0,0 +1,117 @@
|
||||
import 'dart:convert';
|
||||
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_hooks/flutter_hooks.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:hooks_riverpod/hooks_riverpod.dart';
|
||||
import 'package:intl/intl.dart';
|
||||
|
||||
import 'package:loading_animation_widget/loading_animation_widget.dart';
|
||||
|
||||
import '../app/constant.dart';
|
||||
|
||||
import '../provider/current_user_provider.dart';
|
||||
|
||||
import '../screen/home_screen/pending_work_provider.dart';
|
||||
|
||||
import '../screen/work_list_screen/work_list_provider.dart';
|
||||
import 'open_pdf_widget.dart';
|
||||
|
||||
Future<void> RptDate(BuildContext context, WidgetRef ref, String courierID) {
|
||||
return showDialog<void>(
|
||||
context: context,
|
||||
barrierDismissible: true, // user must tap button!
|
||||
builder: (BuildContext context) {
|
||||
return AlertDialog(
|
||||
title: Text(
|
||||
'Pilih Tanggal',
|
||||
style: Constant.heading4(context: context).copyWith(
|
||||
color: Constant.primaryBlue, fontWeight: FontWeight.w600),
|
||||
),
|
||||
shape: const RoundedRectangleBorder(
|
||||
borderRadius: BorderRadius.all(Radius.circular(12))),
|
||||
content: HookConsumer(builder: (context, WidgetRef ref, z) {
|
||||
final dpKey = useState(1);
|
||||
final dateInput = useTextEditingController(
|
||||
text: DateFormat('yyyy-MM-dd').format(DateTime.now()));
|
||||
useEffect(() {
|
||||
WidgetsBinding.instance.addPostFrameCallback((timeStamp) async {
|
||||
var ky = dpKey.value;
|
||||
dpKey.value = ky + 1;
|
||||
});
|
||||
return () {};
|
||||
}, []);
|
||||
|
||||
return SingleChildScrollView(
|
||||
child: Container(
|
||||
width: double.infinity,
|
||||
child: Column(
|
||||
mainAxisAlignment: MainAxisAlignment.start,
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
// SizedBox(
|
||||
// height: Constant.getActualY(context: context, y: 12),
|
||||
// ),
|
||||
TextField(
|
||||
controller: dateInput,
|
||||
decoration: InputDecoration(
|
||||
suffixIcon: Icon(Icons.calendar_today),
|
||||
border: OutlineInputBorder(),
|
||||
labelText: "Pilih Tanggal" //label text of field
|
||||
),
|
||||
readOnly: true,
|
||||
onTap: () async {
|
||||
DateTime? pickedDate = await showDatePicker(
|
||||
context: context,
|
||||
initialDate: DateTime.parse(dateInput.text),
|
||||
firstDate: DateTime(1950),
|
||||
initialEntryMode:
|
||||
DatePickerEntryMode.calendarOnly,
|
||||
//DateTime.now() - not to allow to choose before today.
|
||||
lastDate: DateTime(2100));
|
||||
|
||||
if (pickedDate != null) {
|
||||
print(
|
||||
pickedDate); //pickedDate output format => 2021-03-10 00:00:00.000
|
||||
String formattedDate =
|
||||
DateFormat('yyyy-MM-dd').format(pickedDate);
|
||||
print(
|
||||
formattedDate); //formatted date output using intl package => 2021-03-16
|
||||
dateInput.text =
|
||||
formattedDate; //set output date to TextField value.
|
||||
} else {}
|
||||
},
|
||||
),
|
||||
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 12),
|
||||
),
|
||||
Row(
|
||||
mainAxisAlignment: MainAxisAlignment.end,
|
||||
children: [
|
||||
ElevatedButton(
|
||||
onPressed: () {
|
||||
Navigator.pop(context);
|
||||
Navigator.push(
|
||||
context,
|
||||
MaterialPageRoute(
|
||||
builder: (context) => PdfViewerPage(
|
||||
date: dateInput.text,
|
||||
courierID: courierID),
|
||||
));
|
||||
// print(dateInput.text);
|
||||
},
|
||||
style: ElevatedButton.styleFrom(
|
||||
backgroundColor: Constant.primaryBlue,
|
||||
shape: RoundedRectangleBorder(
|
||||
borderRadius: BorderRadius.circular(8))),
|
||||
child: Text("Buka Rpt")),
|
||||
],
|
||||
),
|
||||
],
|
||||
)));
|
||||
}),
|
||||
);
|
||||
},
|
||||
);
|
||||
}
|
||||
442
lib/widget/sas_textfield.dart
Normal file
442
lib/widget/sas_textfield.dart
Normal file
@@ -0,0 +1,442 @@
|
||||
import 'package:flutter/material.dart';
|
||||
|
||||
import '../../app/constant.dart';
|
||||
|
||||
// define condition START
|
||||
// ketika textfield terisi
|
||||
InputBorder enabledBorderFillTextField = OutlineInputBorder(
|
||||
borderRadius: const BorderRadius.all(Radius.circular(8)),
|
||||
borderSide: BorderSide(
|
||||
color: Constant.primaryMain,
|
||||
width: 2,
|
||||
),
|
||||
);
|
||||
|
||||
// ketika focus
|
||||
InputBorder enabledBorderFocusTextField = OutlineInputBorder(
|
||||
borderRadius: const BorderRadius.all(Radius.circular(8)),
|
||||
borderSide: BorderSide(
|
||||
color: Constant.primaryMain,
|
||||
width: 2,
|
||||
),
|
||||
);
|
||||
|
||||
// ketika no action
|
||||
InputBorder enabledBorderNoAction = OutlineInputBorder(
|
||||
borderRadius: const BorderRadius.all(Radius.circular(8)),
|
||||
borderSide: BorderSide(
|
||||
color: Constant.textGrey,
|
||||
width: 2,
|
||||
),
|
||||
);
|
||||
|
||||
// color ketika focus
|
||||
Color colorFocus = Constant.primaryMain;
|
||||
|
||||
// define condition END
|
||||
|
||||
// color no action
|
||||
Color colorNoAction = Constant.textGrey;
|
||||
|
||||
// Textfield biasa atau common (widget biasa tanpa prefix dan suffix icon)
|
||||
class SasTextField extends StatelessWidget {
|
||||
final String hintText;
|
||||
final String labelText;
|
||||
final String errorText;
|
||||
final void Function()? onToggle;
|
||||
final TextEditingController? controller;
|
||||
final void Function(String)? onChange;
|
||||
final void Function(String)? onSubmitted;
|
||||
final void Function()? onTap;
|
||||
final void Function()? onEditingComplete;
|
||||
final FocusNode? focusNode;
|
||||
|
||||
final bool isError;
|
||||
final bool isReadOnly;
|
||||
|
||||
final bool hasFocus;
|
||||
final TextStyle? style;
|
||||
|
||||
const SasTextField(
|
||||
{Key? key,
|
||||
required this.hintText,
|
||||
required this.labelText,
|
||||
this.onToggle,
|
||||
required this.controller,
|
||||
this.onChange,
|
||||
this.onSubmitted,
|
||||
this.focusNode,
|
||||
this.isError = false,
|
||||
this.isReadOnly = false,
|
||||
this.hasFocus = false,
|
||||
this.onTap,
|
||||
this.onEditingComplete,
|
||||
this.style,
|
||||
this.errorText = ""})
|
||||
: super(key: key);
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return TextField(
|
||||
autofocus: false,
|
||||
showCursor: (hasFocus && isReadOnly == false) ? true : false,
|
||||
readOnly: isReadOnly,
|
||||
controller: controller,
|
||||
enableInteractiveSelection: false,
|
||||
style: style,
|
||||
onChanged: onChange,
|
||||
onSubmitted: onSubmitted,
|
||||
onTap: onTap,
|
||||
onEditingComplete: onEditingComplete,
|
||||
focusNode: focusNode,
|
||||
maxLines: 1,
|
||||
cursorColor: Constant.primaryBlue,
|
||||
decoration: InputDecoration(
|
||||
errorText: (isError) ? errorText : null,
|
||||
// filled: true,
|
||||
fillColor: (hasFocus && isReadOnly == false)
|
||||
? colorFocus
|
||||
: ((controller?.text != "") && isReadOnly == false)
|
||||
? colorFocus
|
||||
: colorNoAction,
|
||||
// filled: true,
|
||||
focusedBorder:
|
||||
(hasFocus && isReadOnly == false) ? enabledBorderFocusTextField : enabledBorderNoAction,
|
||||
enabledBorder: (controller?.text != "" && isReadOnly == false)
|
||||
? enabledBorderFillTextField
|
||||
: (hasFocus && isReadOnly == false)
|
||||
? enabledBorderFocusTextField
|
||||
: enabledBorderNoAction,
|
||||
hintStyle: Constant.body1(context: context).copyWith(
|
||||
color: (hasFocus && isReadOnly == false)
|
||||
? colorFocus
|
||||
: ((controller?.text != "") && isReadOnly == false)
|
||||
? colorFocus
|
||||
: colorNoAction,
|
||||
),
|
||||
// mainkan focus
|
||||
labelStyle: Constant.body1(context: context).copyWith(
|
||||
color: (hasFocus && isReadOnly == false)
|
||||
? colorFocus
|
||||
: ((controller?.text != "") && isReadOnly == false)
|
||||
? colorFocus
|
||||
: colorNoAction,
|
||||
),
|
||||
labelText: labelText,
|
||||
hintText: hintText,
|
||||
alignLabelWithHint: true,
|
||||
border: OutlineInputBorder(
|
||||
borderRadius: BorderRadius.circular(8),
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
// Textfield password (widget dengan suffix icon eye)
|
||||
class SasTextFieldPassword extends StatelessWidget {
|
||||
final String hintText;
|
||||
final String labelText;
|
||||
final String errorText;
|
||||
final bool obscureText;
|
||||
final bool isMaxLine;
|
||||
final void Function()? onToggle;
|
||||
final TextEditingController? controller;
|
||||
final void Function(String)? onChange;
|
||||
final void Function(String)? onSubmitted;
|
||||
final void Function()? onTap;
|
||||
final void Function()? onEditingComplete;
|
||||
final FocusNode? focusNode;
|
||||
|
||||
final bool isError;
|
||||
final bool isReadOnly;
|
||||
|
||||
final bool hasFocus;
|
||||
final TextStyle? style;
|
||||
|
||||
const SasTextFieldPassword(
|
||||
{Key? key,
|
||||
required this.hintText,
|
||||
required this.labelText,
|
||||
this.isMaxLine = false,
|
||||
this.onToggle,
|
||||
this.obscureText = false,
|
||||
required this.controller,
|
||||
this.onChange,
|
||||
this.onSubmitted,
|
||||
this.focusNode,
|
||||
this.isError = false,
|
||||
this.isReadOnly = false,
|
||||
this.hasFocus = false,
|
||||
this.onTap,
|
||||
this.onEditingComplete,
|
||||
this.style,
|
||||
this.errorText = ""})
|
||||
: super(key: key);
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return TextField(
|
||||
autofocus: false,
|
||||
showCursor: (hasFocus) ? true : false,
|
||||
readOnly: isReadOnly,
|
||||
controller: controller,
|
||||
// enableInteractiveSelection: false,
|
||||
style: style,
|
||||
obscureText: obscureText,
|
||||
onChanged: onChange,
|
||||
onSubmitted: onSubmitted,
|
||||
onTap: onTap,
|
||||
onEditingComplete: onEditingComplete,
|
||||
focusNode: focusNode,
|
||||
maxLines: 1,
|
||||
cursorColor: Constant.primaryBlue,
|
||||
decoration: InputDecoration(
|
||||
// fillColor: (hasFocus) ? Constant.primaryMain : Constant.textGrey,
|
||||
errorText: (isError) ? errorText : null,
|
||||
// filled: true,
|
||||
fillColor: (hasFocus)
|
||||
? colorFocus
|
||||
: ((controller?.text != ""))
|
||||
? colorFocus
|
||||
: colorNoAction,
|
||||
// filled: true,
|
||||
focusedBorder:
|
||||
(hasFocus) ? enabledBorderFocusTextField : enabledBorderNoAction,
|
||||
enabledBorder: (controller?.text != "")
|
||||
? enabledBorderFillTextField
|
||||
: (hasFocus)
|
||||
? enabledBorderFocusTextField
|
||||
: enabledBorderNoAction,
|
||||
hintStyle: Constant.body1(context: context).copyWith(
|
||||
color: (hasFocus)
|
||||
? colorFocus
|
||||
: ((controller?.text != ""))
|
||||
? colorFocus
|
||||
: colorNoAction,
|
||||
),
|
||||
// mainkan focus
|
||||
labelStyle: Constant.body1(context: context).copyWith(
|
||||
color: (hasFocus)
|
||||
? colorFocus
|
||||
: ((controller?.text != ""))
|
||||
? colorFocus
|
||||
: colorNoAction,
|
||||
),
|
||||
labelText: labelText,
|
||||
hintText: hintText,
|
||||
alignLabelWithHint: true,
|
||||
border: OutlineInputBorder(
|
||||
borderRadius: BorderRadius.circular(8),
|
||||
),
|
||||
suffixIcon: IconButton(
|
||||
alignment: Alignment.centerRight,
|
||||
onPressed: onToggle,
|
||||
icon: Icon(
|
||||
Icons.remove_red_eye,
|
||||
color: (hasFocus) ? Constant.primaryMain : Constant.textGrey,
|
||||
),
|
||||
iconSize: Constant.getActualY(context: context, y: 24),
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
// Textfield area (widget seperti text area di html)
|
||||
class SasTextFieldArea extends StatelessWidget {
|
||||
final String hintText;
|
||||
final String labelText;
|
||||
final void Function()? onToggle;
|
||||
final TextEditingController? controller;
|
||||
final void Function(String)? onChange;
|
||||
final void Function(String)? onSubmitted;
|
||||
final void Function()? onTap;
|
||||
final void Function()? onEditingComplete;
|
||||
final FocusNode? focusNode;
|
||||
|
||||
final bool isError;
|
||||
final bool isReadOnly;
|
||||
|
||||
final bool hasFocus;
|
||||
final TextStyle? style;
|
||||
|
||||
const SasTextFieldArea(
|
||||
{Key? key,
|
||||
required this.hintText,
|
||||
required this.labelText,
|
||||
this.onToggle,
|
||||
required this.controller,
|
||||
this.onChange,
|
||||
this.onSubmitted,
|
||||
this.focusNode,
|
||||
this.isError = false,
|
||||
this.isReadOnly = false,
|
||||
this.hasFocus = false,
|
||||
this.onTap,
|
||||
this.onEditingComplete,
|
||||
this.style})
|
||||
: super(key: key);
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return TextField(
|
||||
autofocus: false,
|
||||
showCursor: (hasFocus && isReadOnly == false) ? true : false,
|
||||
readOnly: isReadOnly,
|
||||
controller: controller,
|
||||
enableInteractiveSelection: false,
|
||||
style: style,
|
||||
onChanged: onChange,
|
||||
onSubmitted: onSubmitted,
|
||||
onTap: onTap,
|
||||
onEditingComplete: onEditingComplete,
|
||||
focusNode: focusNode,
|
||||
maxLines: 4,
|
||||
cursorColor: Constant.primaryBlue,
|
||||
decoration: InputDecoration(
|
||||
fillColor: (hasFocus && isReadOnly == false)
|
||||
? colorFocus
|
||||
: ((controller?.text != "") && isReadOnly == false)
|
||||
? colorFocus
|
||||
: colorNoAction,
|
||||
// filled: true,
|
||||
focusedBorder:
|
||||
(hasFocus && isReadOnly == false) ? enabledBorderFocusTextField : enabledBorderNoAction,
|
||||
enabledBorder: (controller?.text != "" && isReadOnly == false)
|
||||
? enabledBorderFillTextField
|
||||
: (hasFocus && isReadOnly == false)
|
||||
? enabledBorderFocusTextField
|
||||
: enabledBorderNoAction,
|
||||
hintStyle: Constant.body1(context: context).copyWith(
|
||||
color: (hasFocus && isReadOnly == false)
|
||||
? colorFocus
|
||||
: ((controller?.text != "") && isReadOnly == false)
|
||||
? colorFocus
|
||||
: colorNoAction,
|
||||
),
|
||||
// mainkan focus
|
||||
labelStyle: Constant.body1(context: context).copyWith(
|
||||
color: (hasFocus && isReadOnly == false)
|
||||
? colorFocus
|
||||
: ((controller?.text != "") && isReadOnly == false)
|
||||
? colorFocus
|
||||
: colorNoAction,
|
||||
),
|
||||
labelText: labelText,
|
||||
hintText: hintText,
|
||||
alignLabelWithHint: true,
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
// Textfield search (widget dengan suffix icon search)
|
||||
class SasTextFieldSearch extends StatelessWidget {
|
||||
final String hintText;
|
||||
final String labelText;
|
||||
final String errorText;
|
||||
final bool obscureText;
|
||||
final bool isMaxLine;
|
||||
final void Function()? onPressed;
|
||||
final TextEditingController? controller;
|
||||
final void Function(String)? onChange;
|
||||
final void Function(String)? onSubmitted;
|
||||
final void Function()? onTap;
|
||||
final void Function()? onEditingComplete;
|
||||
final FocusNode? focusNode;
|
||||
|
||||
final bool isError;
|
||||
final bool isReadOnly;
|
||||
|
||||
final bool hasFocus;
|
||||
final TextStyle? style;
|
||||
|
||||
const SasTextFieldSearch(
|
||||
{Key? key,
|
||||
required this.hintText,
|
||||
required this.labelText,
|
||||
this.isMaxLine = false,
|
||||
this.onPressed,
|
||||
this.obscureText = false,
|
||||
required this.controller,
|
||||
this.onChange,
|
||||
this.onSubmitted,
|
||||
this.focusNode,
|
||||
this.isError = false,
|
||||
this.isReadOnly = false,
|
||||
this.hasFocus = false,
|
||||
this.onTap,
|
||||
this.onEditingComplete,
|
||||
this.style,
|
||||
this.errorText = ""})
|
||||
: super(key: key);
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return TextField(
|
||||
autofocus: false,
|
||||
showCursor: (hasFocus) ? true : false,
|
||||
readOnly: isReadOnly,
|
||||
controller: controller,
|
||||
// enableInteractiveSelection: false,
|
||||
style: style,
|
||||
// obscureText: obscureText,
|
||||
onChanged: onChange,
|
||||
onSubmitted: onSubmitted,
|
||||
onTap: onTap,
|
||||
onEditingComplete: onEditingComplete,
|
||||
focusNode: focusNode,
|
||||
maxLines: 1,
|
||||
cursorColor: Constant.primaryBlue,
|
||||
decoration: InputDecoration(
|
||||
// fillColor: (hasFocus) ? Constant.primaryMain : Constant.textGrey,
|
||||
errorText: (isError) ? errorText : null,
|
||||
// filled: true,
|
||||
fillColor: (hasFocus)
|
||||
? colorFocus
|
||||
: ((controller?.text != ""))
|
||||
? colorFocus
|
||||
: colorNoAction,
|
||||
// filled: true,
|
||||
focusedBorder:
|
||||
(hasFocus) ? enabledBorderFocusTextField : enabledBorderNoAction,
|
||||
enabledBorder: (controller?.text != "")
|
||||
? enabledBorderFillTextField
|
||||
: (hasFocus)
|
||||
? enabledBorderFocusTextField
|
||||
: enabledBorderNoAction,
|
||||
hintStyle: Constant.body1(context: context).copyWith(
|
||||
color: (hasFocus)
|
||||
? colorFocus
|
||||
: ((controller?.text != ""))
|
||||
? colorFocus
|
||||
: colorNoAction,
|
||||
),
|
||||
// mainkan focus
|
||||
labelStyle: Constant.body1(context: context).copyWith(
|
||||
color: (hasFocus)
|
||||
? colorFocus
|
||||
: ((controller?.text != ""))
|
||||
? colorFocus
|
||||
: colorNoAction,
|
||||
),
|
||||
labelText: labelText,
|
||||
hintText: hintText,
|
||||
alignLabelWithHint: true,
|
||||
border: OutlineInputBorder(
|
||||
borderRadius: BorderRadius.circular(8),
|
||||
),
|
||||
suffixIcon: IconButton(
|
||||
alignment: Alignment.centerRight,
|
||||
onPressed: onPressed,
|
||||
icon: Icon(
|
||||
Icons.search_rounded,
|
||||
color: (hasFocus) ? Constant.primaryMain : Constant.textGrey,
|
||||
),
|
||||
iconSize: Constant.getActualY(context: context, y: 24),
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
50
lib/widget/snackbar_widget.dart
Normal file
50
lib/widget/snackbar_widget.dart
Normal file
@@ -0,0 +1,50 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:top_snackbar_flutter/custom_snack_bar.dart';
|
||||
import 'package:top_snackbar_flutter/top_snack_bar.dart';
|
||||
|
||||
enum snackbarType { error, info, success, warning }
|
||||
|
||||
SanckbarWidget(BuildContext context, String msg, snackbarType tipe) {
|
||||
switch (tipe) {
|
||||
case snackbarType.error:
|
||||
return showTopSnackBar(
|
||||
Overlay.of(context),
|
||||
CustomSnackBar.error(
|
||||
message: msg,
|
||||
),
|
||||
);
|
||||
break;
|
||||
case snackbarType.success:
|
||||
return showTopSnackBar(
|
||||
Overlay.of(context),
|
||||
CustomSnackBar.success(
|
||||
message: msg,
|
||||
),
|
||||
);
|
||||
break;
|
||||
case snackbarType.info:
|
||||
return showTopSnackBar(
|
||||
Overlay.of(context),
|
||||
CustomSnackBar.info(
|
||||
message: msg,
|
||||
),
|
||||
);
|
||||
break;
|
||||
case snackbarType.warning:
|
||||
return showTopSnackBar(
|
||||
Overlay.of(context),
|
||||
CustomSnackBar.info(
|
||||
backgroundColor: Colors.orangeAccent,
|
||||
message: msg,
|
||||
),
|
||||
);
|
||||
break;
|
||||
default:
|
||||
return showTopSnackBar(
|
||||
Overlay.of(context),
|
||||
CustomSnackBar.info(
|
||||
message: msg,
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
282
lib/widget/work_card.dart
Normal file
282
lib/widget/work_card.dart
Normal file
@@ -0,0 +1,282 @@
|
||||
import 'package:dotted_line/dotted_line.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:hooks_riverpod/hooks_riverpod.dart';
|
||||
import '../models/work_list_model.dart';
|
||||
import '/screen/work_process_screen/work_process_screen.dart';
|
||||
|
||||
import '../../app/constant.dart';
|
||||
import '../../app/route.dart';
|
||||
import '../../models/pending_work_model.dart';
|
||||
import '../provider/current_user_provider.dart';
|
||||
import 'chip_type.dart';
|
||||
|
||||
class WorkCardWidget extends HookConsumerWidget {
|
||||
const WorkCardWidget({super.key, required this.data});
|
||||
|
||||
final WorkListModel data;
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context, WidgetRef ref) {
|
||||
Widget cardValue(String name, String value) {
|
||||
return Row(
|
||||
mainAxisAlignment: MainAxisAlignment.start,
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Expanded(
|
||||
child: Text(
|
||||
name,
|
||||
style: Constant.caption1(context: context).copyWith(
|
||||
fontWeight: FontWeight.w400, color: Constant.textPrimary),
|
||||
),
|
||||
),
|
||||
Text(
|
||||
": ",
|
||||
style: Constant.caption2(context: context).copyWith(
|
||||
fontWeight: FontWeight.w400, color: Constant.textPrimary),
|
||||
),
|
||||
Expanded(
|
||||
child: Text(
|
||||
"${value}",
|
||||
style: Constant.caption1(context: context).copyWith(
|
||||
fontWeight: FontWeight.w400, color: Constant.textPrimary),
|
||||
),
|
||||
),
|
||||
],
|
||||
);
|
||||
}
|
||||
|
||||
return Container(
|
||||
margin: EdgeInsets.symmetric(
|
||||
vertical: Constant.getActualY(context: context, y: 4)),
|
||||
// color: Colors.blue,
|
||||
// height: Constant.getActualY(context: context, y: 170),
|
||||
width: double.infinity,
|
||||
child: Card(
|
||||
shape: RoundedRectangleBorder(borderRadius: BorderRadius.circular(12)),
|
||||
child: Container(
|
||||
decoration: BoxDecoration(
|
||||
color: Colors.white,
|
||||
border: Border.all(color: Colors.grey, width: 0.1),
|
||||
boxShadow: [
|
||||
BoxShadow(
|
||||
color: Color(0XFF919EAB).withOpacity(0.12),
|
||||
offset: Offset(0.0, 12), //(x,y)
|
||||
blurRadius: 24,
|
||||
spreadRadius: -4),
|
||||
BoxShadow(
|
||||
color: Color(0XFF919EAB).withOpacity(0.2),
|
||||
offset: Offset(0.0, 0), //(x,y)
|
||||
blurRadius: 2,
|
||||
),
|
||||
],
|
||||
borderRadius: BorderRadius.circular(12)),
|
||||
child: ElevatedButton(
|
||||
style: ElevatedButton.styleFrom(
|
||||
elevation: 0.2,
|
||||
shape: RoundedRectangleBorder(
|
||||
side: BorderSide(width: 0.1, color: Colors.grey),
|
||||
borderRadius: BorderRadius.circular(12),
|
||||
),
|
||||
backgroundColor: Colors.white,
|
||||
foregroundColor: Colors.grey),
|
||||
onPressed: () {
|
||||
if (data.supervisor == "Dikonfirmasi") {
|
||||
Navigator.pushNamed(
|
||||
context,
|
||||
workProcessRoute,
|
||||
arguments: DetailWorkProp(
|
||||
data.tipeid!,
|
||||
ref.watch(currentUserProvider)?.model.user?.mCourierID ??
|
||||
"0",
|
||||
data.id.toString(),
|
||||
data.noLab.toString(),
|
||||
data.nama.toString(),
|
||||
data.note.toString()),
|
||||
);
|
||||
}
|
||||
},
|
||||
child: Padding(
|
||||
padding: EdgeInsets.symmetric(
|
||||
horizontal: Constant.getActualX(context: context, x: 18),
|
||||
vertical: Constant.getActualY(context: context, y: 20)),
|
||||
child: Column(
|
||||
mainAxisAlignment: MainAxisAlignment.start,
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
children: [
|
||||
ChipType(
|
||||
tipe: data.tipeid!,
|
||||
name: data.tipe!,
|
||||
isDetailHistory: false),
|
||||
if (data.supervisor == "Dikonfirmasi")
|
||||
Icon(
|
||||
Icons.check_circle_outline_rounded,
|
||||
color: Constant.primaryGreen,
|
||||
size: 15,
|
||||
),
|
||||
if (data.supervisor == "Belum dikonfirmasi")
|
||||
Icon(
|
||||
Icons.help_outline_rounded,
|
||||
color: Constant.primaryOrange,
|
||||
size: 15,
|
||||
),
|
||||
if (data.supervisor == "Ditoalk")
|
||||
Icon(
|
||||
Icons.cancel_outlined,
|
||||
color: Constant.primaryRed,
|
||||
size: 15,
|
||||
),
|
||||
],
|
||||
),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 12),
|
||||
),
|
||||
if (data.tipeid == 1)
|
||||
Column(
|
||||
children: [
|
||||
cardValue("Nomot Lab", data.noLab ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Nama", data.nama ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Cabang Pengirim", data.branchname ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Alamat Pengantaran", data.alamat ?? ""),
|
||||
],
|
||||
),
|
||||
if (data.tipeid == 2)
|
||||
Column(
|
||||
children: [
|
||||
cardValue("Nomot Surat Jalan", data.noSuratJalan ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Nama", data.nama ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Cabang Pengirim", data.branchname ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Alamat Pengantaran", data.alamat ?? ""),
|
||||
],
|
||||
),
|
||||
if (data.tipeid == 3)
|
||||
Column(
|
||||
children: [
|
||||
cardValue("Nomot Surat Jalan", data.noSuratJalan ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Nama", data.nama ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Cabang Pengirim", data.branchname ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Alamat Pengantaran", data.alamat ?? ""),
|
||||
],
|
||||
),
|
||||
if (data.tipeid == 4)
|
||||
Column(
|
||||
children: [
|
||||
cardValue("Catatan", data.note ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Pengirim", data.branchaddress ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Penerima", data.alamat ?? ""),
|
||||
],
|
||||
),
|
||||
if (data.tipeid == 5)
|
||||
Column(
|
||||
children: [
|
||||
cardValue("Tujuan", data.nama ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Alamat", data.branchaddress ?? ""),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 5),
|
||||
),
|
||||
cardValue("Cabang penerima", data.branchname ?? ""),
|
||||
],
|
||||
),
|
||||
SizedBox(
|
||||
height: Constant.getActualY(context: context, y: 16),
|
||||
),
|
||||
Row(
|
||||
children: [
|
||||
Icon(
|
||||
Icons.circle_outlined,
|
||||
color: Colors.grey.shade300,
|
||||
size: 15,
|
||||
),
|
||||
SizedBox(
|
||||
width: Constant.getActualX(context: context, x: 12),
|
||||
),
|
||||
Expanded(
|
||||
flex: 5,
|
||||
child: DottedLine(
|
||||
dashColor: Colors.grey.shade300,
|
||||
)),
|
||||
SizedBox(
|
||||
width: Constant.getActualX(context: context, x: 12),
|
||||
),
|
||||
if (data.statusTransaksi == "Baru")
|
||||
Icon(
|
||||
Icons.circle_outlined,
|
||||
color: Constant.primaryBlue,
|
||||
size: 15,
|
||||
),
|
||||
if (data.statusTransaksi == "Proses")
|
||||
Icon(
|
||||
Icons.circle_outlined,
|
||||
color: Constant.primaryYellow,
|
||||
size: 15,
|
||||
),
|
||||
if (data.statusTransaksi == "Done" ||
|
||||
data.statusTransaksi == "Selesai")
|
||||
Icon(
|
||||
Icons.circle_outlined,
|
||||
color: Constant.primaryGreen,
|
||||
size: 15,
|
||||
),
|
||||
SizedBox(
|
||||
width: Constant.getActualX(context: context, x: 4),
|
||||
),
|
||||
Text(
|
||||
"${data.statusTransaksi}",
|
||||
style: Constant.caption2(context: context)
|
||||
.copyWith(color: Constant.textPrimary),
|
||||
),
|
||||
],
|
||||
)
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user