Solved: How to change value of variable in statefull widget from another widget

Question

Asked by AliMohammed M on November 14, 2021 (source).

I have a variable inside a statefull widget which contains a string value. I called a widget from another dart file. I need to change the value of the variable in statefull widget from this widget. I have tries valuelistanablebuilder but it is only listen to value when function called inside that dart file. Please tell me a way and example code on how to do it.

import 'package:flutter/material.dart';
import 'package:messaging_service/components/app_bar.dart';
import 'package:messaging_service/components/home_pages/all_messages.dart';
import 'package:messaging_service/components/home_pages/stories.dart';
import 'package:messaging_service/components/search_bar.dart';
import 'package:messaging_service/components/strings.dart';
import 'package:messaging_service/components/style.dart';

class HomeMobile extends StatefulWidget {
  const HomeMobile({Key? key}) : super(key: key);

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

class _HomeMobileState extends State<HomeMobile> {
  var currentPage = 'all';
  TextEditingController searchChatController = TextEditingController();
  Widget build(BuildContext context) {
    return Scaffold(
      backgroundColor: lightColor,
      appBar: AppBarHomeMobile(context),
      body: SingleChildScrollView(
        child: Column(
          children: [
            AppBarHomeExtend(),
            const SizedBox(
              height: 10,
            ),
            //To Call a Widget
          ],
        ),
      ),
    );
  }
}

In this AppBarHomeExtend() has some buttons..

Widget AppBarHomeExtend() {
  return Container(
    height: 80,
    decoration: BoxDecoration(
        color: lightColor,
        boxShadow: [
          BoxShadow(color: darkColor, blurRadius: 5),
        ],
        borderRadius: const BorderRadius.only(
            bottomLeft: Radius.circular(35), bottomRight: Radius.circular(35))),
    child: Row(
      mainAxisAlignment: MainAxisAlignment.spaceAround,
      children: [
        HRButtons('All Messages', () {}),
        HRButtons('Groups', () {  }),
        HRButtons('Stories', () {}),
        HRButtons('Calls', () {}),
      ],
    ),
  );
}

When called these buttons I need to change the value of variable currentPage from that statefull widget.

Answer

Question answered by Roslan A (source).

First, turn your AppBarHomeExtend into a proper widget which takes a callback function as argument:

import 'package:flutter/material.dart';

class ExtendedAppBar extends StatelessWidget {
  final void Function(String) setPage;

  const ExtendedAppBar({Key? key, required this.setPage}) : super(key: key);

  @override
  Widget build(BuildContext context) {
    return Container(
      height: 80,
      decoration: BoxDecoration(
          color: Colors.blue.shade50,
          boxShadow: [
            BoxShadow(color: Colors.blue.shade900, blurRadius: 5),
          ],
          borderRadius: const BorderRadius.only(bottomLeft: Radius.circular(35), bottomRight: Radius.circular(35))),
      child: Row(
        mainAxisAlignment: MainAxisAlignment.spaceAround,
        children: [
          HRButtons('All Messages', () => setPage('All Messages')),
          HRButtons('Groups', () => setPage('Groups')),
          HRButtons('Stories', () => setPage('Stories')),
          HRButtons('Calls', () => setPage('Calls')),
        ],
      ),
    );
  }
}

Then in your _HomeMobileState class, use this:

ExtendedAppBar(
  setPage: (String value) {
    setState(() {
      currentPage = value;
    });
  },
),
DART FLUTTER
SHARE: