LostTexan
LostTexan

Reputation: 891

Passing parameters from one screen to another using TextFields

I want to pass data that has been entered in a TextField to another screen.

Here is the initial screen shown to the user.

import 'package:flutter/material.dart';
import '../screens/widgets/address_input.dart';
import '/screens/data_screen.dart';

class StartScreen extends StatelessWidget {
  const StartScreen({super.key});

  @override
  Widget build(BuildContext context) {
    return Center(
      child: Column(
        mainAxisSize: MainAxisSize.min,
        children: [
          const NewAddress(),
          
          OutlinedButton.icon(
            onPressed: () {
              Navigator.push(context,
                  MaterialPageRoute(builder: (context) => const DataScreen(_zipController)));
            },
            style: OutlinedButton.styleFrom(
                backgroundColor: Colors.blue, alignment: Alignment.center),
            icon: const Icon(Icons.dataset, color: Colors.black, size: 50),
            label: const Text(
              'GET PROPERTY',
              style: TextStyle(color: Colors.black, fontSize: 30),
            ),
          ),
        ],
      ),
    );
  }
}

NewAddress() is the class used for displaying the address TextFields. This is the code for this class:

import 'package:flutter/material.dart';

class NewAddress extends StatefulWidget {
  const NewAddress({super.key});

  @override
  State<NewAddress> createState() {
    return _NewAddressState();
  }
}

class _NewAddressState extends State<NewAddress> {
  final _address1Controller = TextEditingController();
  final _address2Controller = TextEditingController();
  final _cityController = TextEditingController();
  final _stateController = TextEditingController();
  final _zipController = TextEditingController();

  @override
  void dispose() {
    _address1Controller.dispose();
    _address2Controller.dispose();
    _cityController.dispose();
    _stateController.dispose();
    _zipController.dispose();
    super.dispose();
  }

  @override
  Widget build(BuildContext context) {
    return Padding(
      padding: const EdgeInsets.all(20),
      child: Column(
        children: [
          TextField(
            keyboardType: TextInputType.streetAddress,
            controller: _address1Controller,
            decoration: const InputDecoration(
              label: Text(
                'Address 1',
                style: TextStyle(fontWeight: FontWeight.bold),
              ),
            ),
          ),
          TextField(
            keyboardType: TextInputType.streetAddress,
            controller: _address2Controller,
            decoration: const InputDecoration(
              label: Text(
                'Address 2',
                style: TextStyle(fontWeight: FontWeight.bold),
              ),
            ),
          ),
          TextField(
            keyboardType: TextInputType.text,
            controller: _cityController,
            decoration: const InputDecoration(
              label: Text(
                'City',
                style: TextStyle(fontWeight: FontWeight.bold),
              ),
            ),
          ),
          TextField(
            keyboardType: TextInputType.text,
            controller: _stateController,
            decoration: const InputDecoration(
              label: Text(
                'State',
                style: TextStyle(fontWeight: FontWeight.bold),
              ),
            ),
          ),
          TextField(
            keyboardType: TextInputType.number,
            controller: _zipController,
            decoration: const InputDecoration(
              label: Text(
                'Zip',
                style: TextStyle(fontWeight: FontWeight.bold),
              ),
            ),
          ),
        ],
      ),
    );
  }
}

In the OnPress event in the StartScreen above, I want to pass the zipcode entered. The text controller for that field is _zipController. I thought I would pass it like this:

 onPressed: () {
              Navigator.push(context,
                  MaterialPageRoute(builder: (context) => const DataScreen(_zipController)));
            },

but I am getting an error on _zipController saying it is undefined. I have imported the file where it is defined and you can see that above.

Finally, I am trying to get the parameter passed to DataScreen. Here is the code for DataScreen

import 'dart:async';
import 'dart:convert';
import 'dart:developer';

import 'package:flutter/material.dart';
import 'package:http/http.dart' as http;

import '../models/property_information_model.dart';
import 'widgets/address_information_card.dart';
import '../screens/widgets/address_input.dart';

class DataScreen extends StatefulWidget {
  final String zipCode;
  const DataScreen(this.zipCode, {super.key});

  @override
  _DataScreenState createState() => _DataScreenState();
}

class _DataScreenState extends State<DataScreen> {
  List<PropertyInformation> propertyList = [];

  bool isLoaded = false;

  Future<void> getItems() async {
    setState(() {
      isLoaded = true;
    });
    var client = http.Client();
    String zipCode = zipCode;

    try {
      var url = Uri.parse(
          "https://realty-mole-property-api.p.rapidapi.com/properties?zipCode=$zipCode");
          
      final response = await client.get(
        url,
        headers: {
          'X-RapidAPI-Key': '51ced1b32emsh509f82e1d58ae16p1ad6e6jsn75d75166a8b4',
          'X-RapidAPI-Host': 'realty-mole-property-api.p.rapidapi.com'
        },
      );

      if (response.statusCode == 200) {
               var jsonData = jsonDecode(response.body);

        for (var element in jsonData) {
          element.removeWhere((key, value) => key == null || value == null);
        }        

        // decode the json
        for (var i in jsonData) {
          propertyList.add(PropertyInformation.fromJson(i));
        }

      } else {
        //print('Status Code: ${response.statusCode}');
      }
    } catch (e) {
      setState(() {
        isLoaded = false;
      });
      log("error $e");
    }

    setState(() {
      isLoaded = false;
    });
  }

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

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: const Center(
          child: Text('Data'),
        ),
      ),
      body: Padding(
        padding: const EdgeInsets.all(8.0),
        child: isLoaded
            ? const Center(
                child: CircularProgressIndicator(),
              )
            : ListView.builder(
                itemCount: propertyList.length,
                itemBuilder: (context, index) {
                  return AddressInformationCard(
                    propertyInfo: propertyList[index],
                  );
                },
              ),
      ),
    );
  }
}

I know I am not doing this right so how do I do it the right way? Thanks

Upvotes: 0

Views: 43

Answers (1)

Buddy
Buddy

Reputation: 280

To pass the zip code value to Datascreen, right this code -

onPressed: () {
  Navigator.push(
    context,
    MaterialPageRoute(
      builder: (context) => DataScreen(_zipController.text),
    ),
  );
},

now, for accessing Passed data in Datascreen - use this code -

Future<void> getItems() async {
  setState(() {
    isLoaded = true;
  });
  
  String zipCode = widget.zipCode; 

 
}

with these changes you can pass the zip code, if you face any error, please let me know

Upvotes: 1

Related Questions