I have created an onboarding screen in flutter with 3 pages. What I'm trying to implement is that when user is on the last page (3rd page) and swipes right to left I want to push a screen (let's say Login Screen). How can I achieve such an effect? I tried wrapping the scaffold that the PageView widget is a child of with gesture detector and set its onHorizontalDragUpdate like so:
onVerticalDragUpdate: (details) {}, //So the gestures don't clash
onHorizontalDragUpdate: (details) {
if (provider.currentPage + 1 == onBoardingData.length) {
if (details.delta.direction > 0) {
Navigator.pushNamedAndRemoveUntil(
context,
RoutesName.loginScreen,
(route) => false,
);
}
}
},
It does not work. Any inputs are appreciated.
Here's the full code:
class OnBoardingScreen extends StatelessWidget {
const OnBoardingScreen({super.key});
@override
Widget build(BuildContext context) {
return Consumer<OnBoardingProvider>(
builder: (_, provider, child) {
return GestureDetector(
onVerticalDragUpdate: (details) {},
onHorizontalDragUpdate: (details) {
if (provider.currentPage + 1 == onBoardingData.length) {
if (details.delta.direction > 0) {
Navigator.pushNamedAndRemoveUntil(
context,
RoutesName.loginScreen,
(route) => false,
);
}
}
},
child: Scaffold(
body: Stack(
children: [
Container(
width: double.maxFinite,
padding: const EdgeInsets.only(top: 180),
decoration: BoxDecoration(
image: DecorationImage(
image: AssetImage(Assets.introBG),
fit: BoxFit.cover,
),
),
child: PageView(
onPageChanged: (value) {
provider.pageChanged(value);
},
children: onBoardingData
.map((page) => _buildOnBoardingPage(page: page))
.toList(),
),
),
Align(
alignment: Alignment.bottomCenter,
child: Padding(
padding: const EdgeInsets.only(bottom: 70),
child: Row(
mainAxisSize: MainAxisSize.min,
children: onBoardingData
.map(
(page) => _buildIndicator(
condition: provider.currentPage ==
onBoardingData.indexOf(page),
),
)
.toList(),
),
),
),
Align(
alignment: Alignment.bottomRight,
child: Padding(
padding: const EdgeInsets.only(bottom: 70, right: 20),
child: GestureDetector(
onTap: () {
Navigator.pushNamedAndRemoveUntil(
context,
RoutesName.loginScreen,
(route) => false,
);
},
child: Text(
provider.currentPage + 1 == onBoardingData.length
? 'Done'
: 'Skip',
style: provider.currentPage + 1 == onBoardingData.length
? titleSemiBold14(color: AppColor.colorFF689E)
: titleMedium14(color: AppColor.color258FC5),
),
),
),
),
],
),
),
);
},
);
}
}
Column _buildOnBoardingPage({required OnBoardingModel page}) {
return Column(
mainAxisSize: MainAxisSize.min,
children: [
Image.asset(page.image, fit: BoxFit.cover),
WidgetUtil.spaceVertical(75),
Text(page.title, style: headlineSemiBold22()),
WidgetUtil.spaceVertical(15),
Padding(
padding: const EdgeInsets.symmetric(horizontal: 30),
child: Text(
page.content,
textAlign: TextAlign.center,
style: titleRegular14(),
),
),
],
);
}
Widget _buildIndicator({required bool condition}) {
return Container(
width: Width.w8,
height: Height.h8,
margin: EdgeInsets.only(right: Width.w4),
decoration: BoxDecoration(
color: condition ? AppColor.color258FC5 : AppColor.colorD9D9D9,
borderRadius: const BorderRadius.all(
Radius.circular(50),
),
),
);
}