Search code examples
fluttershowdialogriverpod

How to display Dialog in Flutter without a Buildcontext inside a HookWidget


How do I show a showDialog without a Buildcontext in the sample code given below which has within a class that extends a HookWidget?

Currently, I am getting an Undefined name 'context'.

I am using the following package for state management of my app:

flutter_hooks: ^0.10.0
hooks_riverpod: ^0.3.0

Sample Code:

class HomeScreen extends HookWidget {
  static String routeName = "/home";

  PageController _pageController = PageController(initialPage: 1);

  dynamic balanceAvailable = 0.0;
  List<TransactionModel> transactionList = [];

  _onRefresh(DragEndDetails details) async {
    showDialog(
        context: context,
        builder: (BuildContext context) {
          return Center(
            child: SizedBox(
              height: MediaQuery.of(context).size.height / 4,
              width: MediaQuery.of(context).size.width / 2,
              child: CircularProgressIndicator(
                valueColor: new AlwaysStoppedAnimation<Color>(Colors.blue),
              ),
            ),
          );
        });
    await Future.delayed(const Duration(seconds: 2));

    Navigator.pop(context);
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: GestureDetector(
        onVerticalDragEnd: _onRefresh,
        child: PageView(
          controller: _pageController,
          children: [
            MenuScreen(),
            HomeBody(
              value: balanceAvailable,
            ),
            TransactionScreen(
              transactionList: transactionList,
              value: balanceAvailable,
            ),
          ],
        ),
      ),
    );
  }
}

Solution

  • You can copy paste run full code below
    You can pass context to _onRefresh
    Step 1: _onRefresh(DragEndDetails details, BuildContext context)
    Step 2: onVerticalDragEnd: (details) => {_onRefresh(details, context)},

    working demo

    enter image description here

    full code

    import 'package:flutter/material.dart';
    import 'package:flutter_hooks/flutter_hooks.dart';
    
    class TransactionModel {}
    
    class HomeScreen extends HookWidget {
      static String routeName = "/home";
    
      PageController _pageController = PageController(initialPage: 1);
    
      dynamic balanceAvailable = 0.0;
      List<TransactionModel> transactionList = [];
    
      _onRefresh(DragEndDetails details, BuildContext context) async {
        showDialog(
            context: context,
            builder: (BuildContext context) {
              return Center(
                child: SizedBox(
                  height: MediaQuery.of(context).size.height / 4,
                  width: MediaQuery.of(context).size.width / 2,
                  child: CircularProgressIndicator(
                    valueColor: new AlwaysStoppedAnimation<Color>(Colors.blue),
                  ),
                ),
              );
            });
        await Future.delayed(const Duration(seconds: 2));
    
        Navigator.pop(context);
      }
    
      @override
      Widget build(BuildContext context) {
        return Scaffold(
          body: GestureDetector(
            onVerticalDragEnd: (details) => {_onRefresh(details, context)},
            child: PageView(
              controller: _pageController,
              children: [
                MenuScreen(),
                HomeBody(),
                TransactionScreen(),
              ],
            ),
          ),
        );
      }
    }
    
    class MenuScreen extends StatelessWidget {
      @override
      Widget build(BuildContext context) {
        return Scaffold(
            appBar: AppBar(
              title: Text("MenuScreen"),
            ),
            body: Center(
              child: Column(
                mainAxisAlignment: MainAxisAlignment.center,
                children: <Widget>[
                  Text(
                    'MenuScreen',
                  ),
                ],
              ),
            ));
      }
    }
    
    class HomeBody extends StatelessWidget {
      @override
      Widget build(BuildContext context) {
        return Scaffold(
            appBar: AppBar(
              title: Text("HomeBody"),
            ),
            body: Center(
              child: Column(
                mainAxisAlignment: MainAxisAlignment.center,
                children: <Widget>[
                  Text(
                    'HomeBody',
                  ),
                ],
              ),
            ));
      }
    }
    
    class TransactionScreen extends StatelessWidget {
      @override
      Widget build(BuildContext context) {
        return Scaffold(
            appBar: AppBar(
              title: Text("TransactionScreen"),
            ),
            body: Center(
              child: Column(
                mainAxisAlignment: MainAxisAlignment.center,
                children: <Widget>[
                  Text(
                    'TransactionScreen',
                  ),
                ],
              ),
            ));
      }
    }
    
    void main() {
      runApp(MyApp());
    }
    
    class MyApp extends StatelessWidget {
      @override
      Widget build(BuildContext context) {
        return MaterialApp(
          title: 'Flutter Demo',
          theme: ThemeData(
            primarySwatch: Colors.blue,
          ),
          home: HomeScreen(),
        );
      }
    }