title: FutureBuilder not waiting for async function to load
body: <p>Edit 3: Here's what it looks like now</p>
  
  <pre><code>  @override
    void initState() {
      super.initState();
      myFuture = genCode();
    }
  </code></pre>
  
  <pre><code>Future&lt;Uint8List&gt; genCode() async {
  print('This should be the start')
  Obj o = await _getAsyncData();
  print('This should be the end');
  return await scanner.generateBarCode(o.str);
  }
  
  Future&lt;Obj&gt; _getAsyncData() async {
  Obj o = await addObj();
  print('Hello');
  print(o.str);
  return o;
  }
  
  Future&lt;Obj&gt; addObj() async {
  final String url = 'APIURL';
  final client = new http.Client();
  final response = await client.post(
  url,
  headers: {HttpHeaders.contentTypeHeader: 'application/json',
  );
  print('Obj added. Received response.');
  Obj o = Obj.fromJSON(json.decode(response.body));
  print(o.str);
  return o;
  }
  </code></pre>
  
  <p>Prints</p>
  
  <pre><code>I/flutter (12991): This should be the start
  I/flutter (12991): This should be the end
  I/flutter (12991): Obj added. Received response.
  I/flutter (12991): 12345
  I/flutter (12991): Hello
  I/flutter (12991): 12345
  </code></pre>
  
  <p>FutureBuilder widget goes straight to this block of code</p>
  
  <pre><code>if (snapshot.hasError) {
  children = &lt;Widget&gt;[
  Icon(
  Icons.error_outline,
  color: Colors.red,
  size: 60,
  ),
  Padding(
  padding: const EdgeInsets.only(top: 16),
  child: Text('Error: ${snapshot.error}'),
  )
  ];
  }
  </code></pre>
  
  <p>It shows the exclamation mark and prints on screen:</p>
  
  <pre><code>Error: NoSuchMethodError: The getter 'str' was called on null.
  Receiver: null
  Tried calling: str
  </code></pre>
  
  <p>Somehow it's ignoring the fact that the async function is still running in the background.</p>
  
  <pre><code>FutureBuilder(
                    future: myFuture, // a previously-obtained Future&lt;String&gt; or null
                    builder: (BuildContext context, AsyncSnapshot snapshot) {
                      List&lt;Widget&gt; children;
                      if (snapshot.hasData) {
                        children = &lt;Widget&gt;[
                          QRDisplayWidget(title: '', bytes: snapshot.data),
                        ];
                      } else if (snapshot.hasError) {
                        children = &lt;Widget&gt;[
                          Icon(
                            Icons.error_outline,
                            color: Colors.red,
                            size: 60,
                          ),
                          Padding(
                            padding: const EdgeInsets.only(top: 16),
                            child: Text('Error: ${snapshot.error}'),
                          )
                        ];
                      } else {
                        children = &lt;Widget&gt;[
                          SizedBox(
                            child: CircularProgressIndicator(),
                            width: 60,
                            height: 60,
                          ),
                          const Padding(
                            padding: EdgeInsets.only(top: 16),
                            child: Text('Awaiting result...'),
                          )
                        ];
                      }
                      return Center(
                        child: Column(
                          mainAxisAlignment: MainAxisAlignment.center,
                          crossAxisAlignment: CrossAxisAlignment.center,
                          children: children,
                        ),
                      );
                    },
                  ),
  </code></pre>
  
  <p>Original Code:</p>
  
  <p>Error: The argument type 'Future Function(BuildContext,
  AsyncSnapshot)' can't be assigned to the parameter type 'Widget Function(BuildContext, AsyncSnapshot)'.</p>
  
  <p>What am I missing? The code is exactly the same as the docs</p>
  
  <pre><code>                FutureBuilder&lt;String&gt;(
                    future: getQRStr(), // a previously-obtained Future&lt;String&gt; or null
                    builder: (BuildContext context, AsyncSnapshot&lt;String&gt; snapshot) async {
                      List&lt;Widget&gt; children;
                      if (snapshot.hasData) {
                        children = &lt;Widget&gt;[
                          QRDisplayWidget(title: '', bytes: getBytes(snapshot)),
                        ];
                      } else if (snapshot.hasError) {
                        children = &lt;Widget&gt;[
                          Icon(
                            Icons.error_outline,
                            color: Colors.red,
                            size: 60,
                          ),
                          Padding(
                            padding: const EdgeInsets.only(top: 16),
                            child: Text('Error: ${snapshot.error}'),
                          )
                        ];
                      } else {
                        children = &lt;Widget&gt;[
                          SizedBox(
                            child: CircularProgressIndicator(),
                            width: 60,
                            height: 60,
                          ),
                          const Padding(
                            padding: EdgeInsets.only(top: 16),
                            child: Text('Awaiting result...'),
                          )
                        ];
                      }
                      return Center(
                        child: Column(
                          mainAxisAlignment: MainAxisAlignment.center,
                          crossAxisAlignment: CrossAxisAlignment.center,
                          children: children,
                        ),
                      );
                    },
                  ),
  </code></pre>
  
  <p>Edit: So I got the FutureBuilder to stop throwing the error, but the String value is still retrieved before the data is fetched.</p>
  
  <pre><code>  Future&lt;String&gt; getQRStr() async{
      String str = await _asyncFetchData();
      return Future.value(str); // return your response
    }
  
    Future&lt;Uint8List&gt; getBytes(AsyncSnapshot snapshot) async{
      return await scanner.generateBarCode(snapshot.data);
    }
  </code></pre>
  
  <p>Edit 2: 
  I edited it to what I have right now. If I use Future on getBytes, I get <code>Error: The argument type 'Future&lt;Uint8List&gt;' can't be assigned to the parameter type 'Uint8List'</code>. Removing Future makes it run compile without errors but the app seems to be thrown into a state of perpetual refresh, constantly calling getQRStr().</p>
  
  <p>Under the _asyncFetchData function, I have a print function that prints the data after successfully retrieving it before returning the value. That prints fine. But FutureBuilder prints that the value returned is null.</p>