[Solved] Flutter Navigate back to home Screen after a time when there is no interaction on the second Screen

Question

Asked by Carlos C on December 01, 2021 (source).

Flutter beginner needs help. Is it possible that the app by himself without a press of a button, navigates from a second screen to the home screen after a period of time, if there is no any interaction on the second Screen. For example in the following code is it possible to make this? I don't know how to implement this. Thanks in advance for some help

import 'package:flutter/material.dart';

void main() => runApp(MyApp());

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: Home(),
    );
  }
}

class Home extends StatefulWidget {
  @override
  _HomeState createState() => _HomeState();
}

class _HomeState extends State<Home> {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
          title: const Text('Navigate to a new screen on Button click'),
          backgroundColor: Colors.teal),
      body: Center(
        child: FlatButton(
          color: Colors.teal,
          textColor: Colors.white,
          onPressed: () {
            Navigator.of(context).push(MaterialPageRoute(builder: (context)=>Screen2()));
          },
          child: Text('GO TO SCREEN 2'),
        ),
      ),
    );
  }
}
class Screen2 extends StatefulWidget {
  @override
  _Screen2State createState() => _Screen2State();
}

class _Screen2State extends State<Screen2> {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
          title: const Text('Navigate to a new screen on Button click'),
          backgroundColor: Colors.blueAccent),
      body: Center(
        child: FlatButton(
          color: Colors.blueAccent,
          textColor: Colors.white,
          onPressed: () {
            Navigator.of(context).push(MaterialPageRoute(builder: (context)=>Home()));

          },
          child: Text('GO TO HOME'),
        ),
      ),
    );
  }
}

Answer

Question answered by david d (source).

First, I would recommend pop and not push because Flutter navigator works like a stack.

Next, you can set a timer in the initState function:

  @override
  void initState() {
    Timer(Duration(seconds: 3), () {
      Navigator.of(context).pop(MaterialPageRoute(builder: (context) => Home()));
    });
    super.initState();
  }

for a better solution, I would set a timer in the initState function and wrap the entire page with GestureDetector, so that each gesture resets the timer.

Use GestureDetector's behavior property and pass HitTestBehavior.opaque to it, which recognizes entire screen and detects the tap when you tap anywhere on the screen. like this:

import 'dart:async';

import 'package:flutter/material.dart';

class Screen2 extends StatefulWidget {
  @override
  _Screen2State createState() => _Screen2State();
}

class _Screen2State extends State<Screen2> {
  Timer? searchOnStoppedTyping;
  _onChangeHandler() {
    const duration = Duration(milliseconds: 800); // set the duration that you want call pop() after that.
    if (searchOnStoppedTyping != null) {
      searchOnStoppedTyping?.cancel(); // clear timer
    }
   searchOnStoppedTyping = new Timer(duration, () => navigateHome());
  }

  navigateHome() {
    Navigator.of(context).pop(MaterialPageRoute(builder: (context) => Home()));
  }

  @override
  void initState() {
    _onChangeHandler();
    super.initState();
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(title: const Text('Navigate to a new screen on Button click'), backgroundColor: Colors.blueAccent),
      body: GestureDetector(
        //Use GestureDetector's behavior property and pass HitTestBehavior.opaque to it, which recognizes entire screen and detects the tap when you tap anywhere on the screen.
          behavior: HitTestBehavior.opaque,
          onTap: _onChangeHandler,
          child: yourBody...,
        ),
    );
  }
}
DART FLUTTER
SHARE: