Код: Выделить всё
import ...
void ridePopUp(BuildContext context, WidgetRef ref, Widget content, VoidCallback? onDone, bool actionVisible) {
showModalBottomSheet(
useRootNavigator: true,
useSafeArea: true,
enableDrag: false,
clipBehavior: Clip.antiAlias,
isScrollControlled: true,
isDismissible: false,
backgroundColor: Colors.transparent,
barrierColor: Colors.transparent,
context: context,
builder: (context) {
return RideBottomPopupSheet(
content: content,
onDone: onDone,
actionVisible: actionVisible,
);
},
);
}
class RideBottomPopupSheet extends ConsumerStatefulWidget {
const RideBottomPopupSheet({
super.key,
required this.content,
required this.actionVisible,
this.onDone,
});
final Widget content;
final VoidCallback? onDone;
final bool actionVisible;
@override
ConsumerState createState() => _RideBottomPopupSheetState();
}
class _RideBottomPopupSheetState extends ConsumerState {
@override
Widget build(BuildContext context) {
return SingleChildScrollView(
child: Padding(
padding: const EdgeInsets.all(10.0)
.copyWith(bottom: MediaQuery.of(context).viewInsets.bottom + 40),
child: Container(
clipBehavior: Clip.antiAlias,
decoration: const BoxDecoration(
borderRadius: BorderRadius.all(
Radius.circular(20),
),
color: Colors.white,
),
child: Column(
children: [
Container(
decoration: const BoxDecoration(
borderRadius: BorderRadius.all(
Radius.circular(20),
),
color: Colors.white,
),
width: double.maxFinite,
child: Padding(
padding: const EdgeInsets.symmetric(vertical: 8),
child: widget.content,
),
),
if (widget.actionVisible) ...[
CustomContainer(
borderRadius: 0,
width: double.maxFinite,
child: TextButton(
style: TextButton.styleFrom(
foregroundColor: Colors.white,
backgroundColor: Constants.primaryColor,
),
clipBehavior: Clip.hardEdge,
onPressed: widget.onDone,
child: Text(
'Continue',
overflow: TextOverflow.fade,
style: GoogleFonts.inter(
fontSize: 16,
fontWeight: FontWeight.w500,
),
),
),
),
],
],
),
),
),
);
}
}
Код: Выделить всё
class BookRideScreen extends ConsumerStatefulWidget {
const BookRideScreen({super.key});
@override
ConsumerState createState() => _BookRideScreenState();
}
class _BookRideScreenState extends ConsumerState {
StateProvider terminalSelected = StateProvider((ref) => 1);
@override
void initState() {
// TODO: implement initState
super.initState();
SystemChrome.setEnabledSystemUIMode(SystemUiMode.edgeToEdge);
WidgetsBinding.instance.addPostFrameCallback((_) {
ridePopUp(
context,
ref,
Column(
mainAxisSize: MainAxisSize.min,
crossAxisAlignment: CrossAxisAlignment.start,
mainAxisAlignment: MainAxisAlignment.start,
children: [
/// FIRST CHOICE --> TERMINAL 1
Padding(
padding: const EdgeInsets.only(left: 18.0),
child: InkWell(
onTap: () {
ref.read(terminalSelected.notifier).update((state) => 1);
},
child: Row(
mainAxisAlignment: MainAxisAlignment.start,
children: [
Consumer(builder: (context, ref, child) {
return Checkbox(
value: ref.watch(terminalSelected) == 1 ? true : false,
materialTapTargetSize: MaterialTapTargetSize.padded,
activeColor: Constants.primaryColor,
shape: const CircleBorder(),
side: const BorderSide(
width: 2,
style: BorderStyle.solid,
color: Color(0xffd9d9d9),
),
onChanged: (bool? value) {
if (value == true) {
ref
.read(terminalSelected.notifier)
.update((state) => 1);
}
},
);
}),
Expanded(
child: ListTile(
contentPadding: EdgeInsets.zero,
title: Text(
'Terminal 1',
style: GoogleFonts.inter(
fontSize: 18,
fontWeight: FontWeight.w500,
color: const Color(0xff344054),
),
),
subtitle: Text(
'Pick Up Point',
style: GoogleFonts.inter(
fontSize: 12,
fontWeight: FontWeight.w500,
color: const Color(0xff344054),
),
),
),
),
],
),
),
),
const Divider(
color: Color(0xffd0d5dd),
thickness: 1.8,
),
/// Second Choice --> TERMINAL 2
Padding(
padding: const EdgeInsets.only(left: 18.0),
child: InkWell(
onTap: () {
ref.read(terminalSelected.notifier).update((state) => 2);
},
child: Row(
mainAxisAlignment: MainAxisAlignment.start,
children: [
Consumer(builder: (context, ref, child) {
return Checkbox(
value: ref.watch(terminalSelected) == 2 ? true : false,
materialTapTargetSize: MaterialTapTargetSize.padded,
activeColor: Constants.primaryColor,
shape: const CircleBorder(),
side: const BorderSide(
width: 2,
style: BorderStyle.solid,
color: Color(0xffd9d9d9),
),
onChanged: (bool? value) {
if (value == true) {
ref
.read(terminalSelected.notifier)
.update((state) => 2);
}
},
);
}),
Expanded(
child: ListTile(
contentPadding: EdgeInsets.zero,
title: Text(
'Terminal 2',
style: GoogleFonts.inter(
fontSize: 18,
fontWeight: FontWeight.w500,
color: const Color(0xff344054),
),
),
subtitle: Text(
'Pick Up Point',
style: GoogleFonts.inter(
fontSize: 12,
fontWeight: FontWeight.w500,
color: const Color(0xff344054),
),
),
),
),
],
),
),
),
const Divider(
color: Color(0xffd0d5dd),
thickness: 1.8,
),
/// THIRD CHOICE --> TERMINAL 3
Padding(
padding: const EdgeInsets.only(left: 18.0),
child: InkWell(
onTap: () {
ref.read(terminalSelected.notifier).update((state) => 3);
},
child: Row(
mainAxisAlignment: MainAxisAlignment.start,
children: [
Consumer(builder: (context, ref, child) {
return Checkbox(
value: ref.watch(terminalSelected) == 3 ? true : false,
materialTapTargetSize: MaterialTapTargetSize.padded,
activeColor: Constants.primaryColor,
shape: const CircleBorder(),
side: const BorderSide(
width: 2,
style: BorderStyle.solid,
color: Color(0xffd9d9d9),
),
onChanged: (bool? value) {
if (value == true) {
ref
.read(terminalSelected.notifier)
.update((state) => 3);
}
},
);
}),
Expanded(
child: ListTile(
contentPadding: EdgeInsets.zero,
title: Text(
'Terminal 3',
style: GoogleFonts.inter(
fontSize: 18,
fontWeight: FontWeight.w500,
color: const Color(0xff344054),
),
),
subtitle: Text(
'Pick Up Point',
style: GoogleFonts.inter(
fontSize: 12,
fontWeight: FontWeight.w500,
color: const Color(0xff344054),
),
),
),
),
],
),
),
),
],
),
() {},
true,
);
});
}
@override
void dispose() {
// TODO: implement dispose
super.dispose();
SystemChrome.setEnabledSystemUIMode(SystemUiMode.manual,
overlays: SystemUiOverlay.values); // to re-show bars
}
@override
Widget build(BuildContext context) {
return Scaffold(
body: Stack(
children: [
const GoogleMap(
initialCameraPosition: CameraPosition(
target: GoogleMapsConstants.terminal1Location,
zoom: 18,
),
),
Positioned(
top: MediaQuery.of(context).viewPadding.top,
child: Row(
mainAxisSize: MainAxisSize.min,
children: [
ElevatedButton(
onPressed: () {},
clipBehavior: Clip.antiAlias,
style: ElevatedButton.styleFrom(
padding: EdgeInsets.zero,
foregroundColor: const Color(0xff344054),
backgroundColor: Colors.white,
shape: const CircleBorder(),
),
child: SvgPicture.asset('assets/svgs/uyufjdx.svg'),
),
const SizedBox(
width: 5,
),
ElevatedButton(
onPressed: () {},
clipBehavior: Clip.antiAlias,
style: ElevatedButton.styleFrom(
foregroundColor: const Color(0xff344054),
backgroundColor: Colors.white,
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.circular(50.0),
),
),
child: SvgPicture.asset('assets/svgs/gutdw.svg'),
),
],
),
),
],
),
);
}
}
ИЗОБРАЖЕНИЕ: Дизайн, который мне нужно реализовать:
[img]https:// i.sstatic.net/kFIXZ.jpg[/img]
Подробнее здесь: https://stackoverflow.com/questions/774 ... ng-the-bot