Case: There is a form where user information is entered. Individuals are shown with this form modal. I want to block the modal's direct connection if the user form has made a login. I'm shown the throw dialog based on the x button. But I cannot prevent this if the modal is closed by dragging. If any information has been entered into the form, the discard dialog should be displayed when trying to close it by dragging. Below is sample code.
import 'package:flutter/material.dart';
void main() => runApp(const NavigatorPopHandlerApp());
class NavigatorPopHandlerApp extends StatelessWidget {
const NavigatorPopHandlerApp({super.key});
@override
Widget build(BuildContext context) {
return MaterialApp(
initialRoute: '/home',
routes: <String, WidgetBuilder>{
'/home': (BuildContext context) => const _HomePage(),
},
);
}
}
class _HomePage extends StatefulWidget {
const _HomePage();
@override
State<_HomePage> createState() => _HomePageState();
}
class _HomePageState extends State<_HomePage> {
@override
Widget build(BuildContext context) {
return Scaffold(
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
const Text('Page One'),
TextButton(
onPressed: () {
showModalBottomSheet<void>(
context: context,
builder: (BuildContext context) {
return const _FormModal();
},
);
},
child: const Text('Show Bottom Sheet'),
),
],
),
),
);
}
}
class _FormModal extends StatefulWidget {
const _FormModal();
@override
State<_FormModal> createState() => _FormModalState();
}
class _FormModalState extends State<_FormModal> {
void _showDiscardDialog() {
showDialog<void>(
context: context,
builder: (BuildContext context) {
return AlertDialog(
title: const Text('Are you sure?'),
content: const Text(
'Are you sure you want to leave this page?',
),
actions: <Widget>[
TextButton(
style: TextButton.styleFrom(
textStyle: Theme.of(context).textTheme.labelLarge,
),
child: const Text('Nevermind'),
onPressed: () {
Navigator.pop(context);
},
),
TextButton(
style: TextButton.styleFrom(
textStyle: Theme.of(context).textTheme.labelLarge,
),
child: const Text('Leave'),
onPressed: () {
Navigator.pop(context);
Navigator.pop(context);
},
),
],
);
},
);
}
@override
Widget build(BuildContext context) {
return Container(
padding: const EdgeInsets.all(16),
child: Column(
children: <Widget>[
Container(color: Colors.black54, height: 4, width: 48),
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
const Text('This is a modal'),
PopScope(
canPop: false,
onPopInvoked: (bool didPop) {
if (didPop) {
return;
}
_showDiscardDialog();
},
child: IconButton(
onPressed: () {
_showDiscardDialog();
},
icon: const Icon(Icons.close),
),
),
],
),
],
),
);
}
}
Please place this code at the beginning of the
_FormModalwidget structure.