To pass a Hive box between screens in Flutter

1,131

Instead of creating new instance of box (in ur case box3) u can directly ref the box2 that u initialised.

 Navigator.of(context)
 .push(
     MaterialPageRoute(
        builder: (context) => Page2(box3: box2),
      )
   );

there is no need of ref as well u can directly initialize particular box in init State as its not async call it will just work fine

Share:
1,131
Harsh Chauhan
Author by

Harsh Chauhan

Updated on December 12, 2022

Comments

  • Harsh Chauhan
    Harsh Chauhan over 1 year

    I'm trying to pass a Hive Box from main screen to the next but am unable to. I tried using Box type while MaterialPageRoute but it didn't work.

    I am accepting data from user and trying CRUD operations on them. I also want to pass a HIve Box from one page to the next

    import 'dart:io';
    import 'package:flutter/material.dart';
    import 'package:fluttertoast/fluttertoast.dart';
    import 'package:hive/hive.dart';
    import 'package:path_provider/path_provider.dart';
    
    void main() async {
      WidgetsFlutterBinding.ensureInitialized();
      Directory dir = await getExternalStorageDirectory();
      Hive.init(dir.path);
      print(dir.path);
      await Hive.openBox<String>('box1');
      runApp(MyApp());
    }
    
    class MyApp extends StatelessWidget {
      // This widget is the root of your application.
      @override
      Widget build(BuildContext context) {
        return MaterialApp(
          title: 'Flutter Demo',
          theme: ThemeData(
            primarySwatch: Colors.blue,
            visualDensity: VisualDensity.adaptivePlatformDensity,
          ),
          home: MyHomePage(title: 'Hive Storage Test Run'),
        );
      }
    }
    
    class MyHomePage extends StatefulWidget {
      MyHomePage({Key key, this.title}) : super(key: key);
    
      final String title;
    
      @override
      _MyHomePageState createState() => _MyHomePageState();
    }
    
    class _MyHomePageState extends State<MyHomePage> {
      String name, pass;
    
      Box<String> box2;
    
      TextEditingController _fullname = TextEditingController();
      TextEditingController _password = TextEditingController();
    
      @override
      void initState() {
        super.initState();
        box2 = Hive.box<String>('box1');
      }
    
      bool _showpass = false;
    
      @override
      Widget build(BuildContext context) {
        return Scaffold(
          appBar: AppBar(
            title: Text(widget.title),
          ),
          body: Center(
            child: Column(
              mainAxisAlignment: MainAxisAlignment.center,
              children: <Widget>[
                //Full name
                TextField(
                  controller: _fullname,
                  decoration: InputDecoration(labelText: 'Enter Full name'),
                  onSubmitted: (String value) {
                    name = value;
                    Fluttertoast.showToast(msg: 'Welcome ${name}');
                  },
                ),
                //Password
                TextField(
                  controller: _password,
                  obscureText: !this._showpass,
                  decoration: InputDecoration(
                    labelText: 'Enter Password',
                    suffixIcon: IconButton(
                      icon: Icon(
                        Icons.remove_red_eye_outlined,
                        color: this._showpass ? Colors.redAccent : Colors.blueAccent,
                      ),
                      onPressed: () {
                        setState(() => this._showpass = !this._showpass);
                      },
                    ),
                  ),
                  onSubmitted: (String value) {
                    pass = value;
                    Fluttertoast.showToast(msg: 'Password is ${pass}');
                  },
                ),
                SizedBox(height: 100,),
                Column(
                  children: <Widget>[
                    Row(
                      mainAxisAlignment: MainAxisAlignment.spaceAround,
                      children: <Widget>[
                        RaisedButton(
                          child: Text('Save'),
                          onPressed: () {
                            final key = _fullname.text;
                            final value = _password.text;
                            box2.put(key, value);
                            print(key);
                            print(value);
                            setState(() {
                              _fullname = TextEditingController(text: "");
                              _password = TextEditingController(text: "");
                            });
                          },
                        ),
                        RaisedButton(
                          child: Text('Print Values'),
                          onPressed: () {
                            print(box2.getAt(0));
                          },
                        ),
                      ],
                    ),
                    SizedBox(height: 30.0,),
                    Row(
                      mainAxisAlignment: MainAxisAlignment.spaceAround,
                      children: <Widget>[
                        RaisedButton(
                          child: Text('Load'),
                          onPressed: () {
                            if(box2.isEmpty == true){
                              Fluttertoast.showToast(msg: "No data present. Please enter new data");
                            }else{
                              Box box3 = box2;
                              Navigator.of(context)
                                  .push(
                                MaterialPageRoute(
                                  builder: (context) => Page2(box3: box3),
                                )
                              );
                            }
                          },
                        ),
                        RaisedButton(
                          child: Text("Empty Data"),
                          onPressed: () {
                            box2.clear();
                          },
                        ),
                      ],
                    ),
                  ],
                ),
              ],
            ),
          ), // This trailing comma makes auto-formatting nicer for build methods.
        );
      }
    }
    
    
    class Page2 extends StatefulWidget {
    
      Box box3;
      Page2({box3});
    
      @override
      _Page2State createState() => _Page2State(box3);
    }
    
    class _Page2State extends State<Page2> {
    
      Box box3;
      _Page2State(this.box3);
    
      @override
      Widget build(BuildContext context) {
        return Scaffold(
          appBar: AppBar(
            title: Text("Page 2"),
          ),
          body: Center(
            child: Column(
              children: <Widget>[
                Text("Page 2"),
                Text(box3.getAt(0)),
                RaisedButton(
                  onPressed: () {
                    child: Text("Back");
                    Navigator.of(context).pop();
                  },
                )
              ],
            ),
          ),
        );
      }
    }
    

    I need to pass box2 from MyHomePage to Page2

    This is my Error ....

    The following NoSuchMethodError was thrown building Page2(dirty, state: _Page2State#33882):
    The method 'getAt' was called on null.
    Receiver: null
    Tried calling: getAt(0)
    
    The relevant error-causing widget was: 
      Page2 file:///C:/Users/harsh/AndroidStudioProjects/storage/lib/main.dart:142:53
    When the exception was thrown, this was the stack: 
    #0      Object.noSuchMethod (dart:core-patch/object_patch.dart:51:5)
    #1      _Page2State.build (package:storage/main.dart:190:23)
    #2      StatefulElement.build (package:flutter/src/widgets/framework.dart:4744:28)
    #3      ComponentElement.performRebuild (package:flutter/src/widgets/framework.dart:4627:15)
    #4      StatefulElement.performRebuild (package:flutter/src/widgets/framework.dart:4800:11)
    ...
    
    • HeIsDying
      HeIsDying over 3 years
      can your show us the error log? and what do you mean by unable?
    • Harsh Chauhan
      Harsh Chauhan over 3 years
      Sorry I shouldn't be using unable. The more proper meaning would be I am just new to this and am unable to debug to error on my own.
  • Harsh Chauhan
    Harsh Chauhan over 3 years
    I tried your Solution. The error still persists. I changed the Text widget in Page 2. Text(box3.getAt(0)) was replaced with Text(box3.get("Harsh")) The error states that method 'get' was called on null.
  • Harsh Chauhan
    Harsh Chauhan over 3 years
    Thank you for help. I got the problem. I only had to delete the datatype specified for the box and it worked