I'm making a toggle button to switch between the unit system, I need to do it using Getx for state management.
This code works, but its using setState() instead
This is the (simplified) code:
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:flutter_toggle_tab/flutter_toggle_tab.dart';
void main() {
runApp(const MyApp());
}
class MyApp extends StatelessWidget {
const MyApp({Key? key}) : super(key: key);
#override
Widget build(BuildContext context) {
return const MaterialApp(
home: MyHomePage(),
);
}
}
class MyHomePage extends StatefulWidget {
const MyHomePage({this.title});
final String? title;
#override
_MyHomePageState createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
var _tabTextIndexSelected = 0;
final _listTextTabToggle = ["km / m", "m / ft"];
#override
Widget build(BuildContext context) {
return SafeArea(
child: Scaffold(
body: SingleChildScrollView(
child: Column(
children:[
FlutterToggleTab(
selectedIndex: _tabTextIndexSelected,
selectedBackgroundColors: const [
Colors.blue,
Colors.blueAccent
],
selectedTextStyle: const TextStyle(
color: Colors.white),
unSelectedTextStyle: const TextStyle(),
labels: _listTextTabToggle,
selectedLabelIndex: (index) {
setState(() {
_tabTextIndexSelected = index;
});
},
isScroll: false,
),
Text(
"Index selected : $_tabTextIndexSelected",
),
],
),
),
),
);
}
}
Tried to add obs to the variable _tabTextIndexSelected and obx to everything that is supposed to change, but it doesn't work.
Also, I'm using https://pub.dev/packages/flutter_toggle_tab
this is what I tried (two codes are from different files, I like to try first rather than doing it in my project):
RxInt _tabTextIndexSelected = 0.obs;
final _listTextTabToggle = ["km / m", "m / ft"];
#override
Widget build(BuildContext context) {
return SafeArea(
child: Scaffold(
body: Column(
children: [
Obx(
()=> FlutterToggleTab(
selectedIndex: _tabTextIndexSelected,
selectedBackgroundColors: const [
Colors.blue,
Colors.blueAccent
],
selectedTextStyle: const TextStyle(
color: Colors.white),
unSelectedTextStyle: const TextStyle(),
labels: _listTextTabToggle,
selectedLabelIndex: (index) {
_tabTextIndexSelected = index.obs;
},
isScroll: false,
),
),
Obx(
()=>Text(
"Index selected : $_tabTextIndexSelected",
),
),
The reactive variable and list of tabs string declaration inside the getx controller.
Below is the working snippet to toggle the tabbar.
import 'package:flutter/material.dart';
import 'package:flutter_toggle_tab/flutter_toggle_tab.dart';
import 'package:get/get.dart';
class TestController extends GetxController {
final listTextTabToggle = ["km / m", "m / ft"];
RxInt tabTextIndexSelected = 0.obs;
toggle(int index) => tabTextIndexSelected.value = index;
}
class TestPage extends StatelessWidget {
const TestPage({Key? key}) : super(key: key);
#override
Widget build(BuildContext context) {
final ctrl = Get.put(TestController());
return SafeArea(
child: Scaffold(
body: Column(children: [
Obx(
() => FlutterToggleTab(
selectedIndex: ctrl.tabTextIndexSelected.value,
selectedBackgroundColors: const [Colors.blue, Colors.blueAccent],
selectedTextStyle: const TextStyle(color: Colors.white),
unSelectedTextStyle: const TextStyle(),
labels: ctrl.listTextTabToggle,
selectedLabelIndex: (index) => ctrl.toggle(index),
isScroll: false,
),
),
Obx(
() => Text(
"Index selected : ${ctrl.tabTextIndexSelected.value}",
),
)
])),
);
}
}
Output:
Related
Class A has 4 tabs, each tab has its own classes and fields, is there a elegant way to validate all the classes/tabs from Class A using Provider architecture.
Take a look at the official tutorial documentation. It's going to explain step by step how to create a model that shares states between other widgets.
I've also made the prototype below and a live demo on DartPad to help you out with your exact problem.
Data
A
B
Summary
No Data
With Data
Below is the code from DartPad as a minimum-reproducible-example. There is the Model provider where the data resides for every widget to access it. The classes A, B, and Summary each one consumes the Model data using the Consumer<Model>. Every time the Model changes it notifies all consumers (the listeners) of the change and then the widgets can be updated with the new data.
import 'package:flutter/material.dart';
import 'package:provider/provider.dart';
enum BEnum {
test1,
test2,
}
class Model extends ChangeNotifier {
String _aText = '';
BEnum? _bEnum;
String get aText => _aText;
BEnum? get bEnum => _bEnum;
setText(String text) {
_aText = text;
notifyListeners();
}
setBEnum(BEnum? bEnum) {
_bEnum = bEnum;
notifyListeners();
}
}
void main() {
runApp(MultiProvider(providers: [
ChangeNotifierProvider(create: (_) => Model()),
], child: const MyApp()));
}
class MyApp extends StatelessWidget {
const MyApp({Key? key}) : super(key: key);
#override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Demo',
theme: ThemeData(
primarySwatch: Colors.blue,
),
home: const MyHomePage(),
debugShowCheckedModeBanner: false,
);
}
}
class MyHomePage extends StatefulWidget {
const MyHomePage({Key? key}) : super(key: key);
#override
State<MyHomePage> createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
var _selectedIndex = 0;
final _tabs = [
const A(),
const B(),
const Summary(),
];
#override
Widget build(BuildContext context) {
return Scaffold(
body: Padding(
padding: const EdgeInsets.all(24),
child: Center(child: _tabs[_selectedIndex]),
),
bottomNavigationBar: BottomNavigationBar(
items: const [
BottomNavigationBarItem(icon: Icon(Icons.abc), label: 'A'),
BottomNavigationBarItem(icon: Icon(Icons.bolt), label: 'B'),
BottomNavigationBarItem(icon: Icon(Icons.list), label: 'Summary'),
],
currentIndex: _selectedIndex,
selectedItemColor: Colors.amber[800],
onTap: _onItemTapped,
),
);
}
void _onItemTapped(int index) {
setState(() {
_selectedIndex = index;
});
}
}
class A extends StatelessWidget {
const A({Key? key}) : super(key: key);
#override
Widget build(BuildContext context) {
return Column(
children: [
const Text(
'A',
style: TextStyle(fontSize: 30, fontWeight: FontWeight.bold),
),
Consumer<Model>(
builder: (context, model, child) {
return TextField(
decoration: const InputDecoration(
border: OutlineInputBorder(),
labelText: 'A',
),
onChanged: (value) => model.setText(value),
);
},
)
],
);
}
}
class B extends StatelessWidget {
const B({Key? key}) : super(key: key);
#override
Widget build(BuildContext context) {
return Consumer<Model>(
builder: (context, model, _) {
return Column(
children: [
const Text(
'B',
style: TextStyle(fontSize: 30, fontWeight: FontWeight.bold),
),
Expanded(
child: ListView.builder(
itemCount: BEnum.values.length,
itemBuilder: (context, index) {
final bEnum = BEnum.values[index];
return RadioListTile<BEnum?>(
title: Text(bEnum.name),
groupValue: model.bEnum,
value: bEnum,
onChanged: (value) => model.setBEnum(value),
);
},
),
),
],
);
},
);
}
}
class Summary extends StatelessWidget {
const Summary({Key? key}) : super(key: key);
#override
Widget build(BuildContext context) {
return Consumer<Model>(
builder: (context, model, _) {
return Column(
children: [
const Text(
'Summary',
style: TextStyle(fontSize: 30, fontWeight: FontWeight.bold),
),
Row(
children: [
const Text('A text: ',
style: TextStyle(fontWeight: FontWeight.bold)),
Text(model.aText),
],
),
Row(
children: [
const Text('B selection: ',
style: TextStyle(fontWeight: FontWeight.bold)),
Text(model.bEnum?.name ?? 'None'),
],
),
],
);
},
);
}
}
I'm building my app with Flutter 2.10.5 and Dart 2.16.2.
When i try to refresh the demo content whith a pull, nothing happens. I have multiple navigation routes for different content. So the demo is a litte bit complex.
The main.dart includes the basic code for the app. I use the NavDrawer Widget to build the different pages. Every route is defined in the navigation.dart file, which reference to the content widgets.
My code so far is:
import 'dart:core';
import 'package:english_words/english_words.dart';
import 'package:flutter/material.dart';
import 'package:flutter/cupertino.dart';
void main() async {
runApp(const MyApp());
}
class MyApp extends StatelessWidget {
const MyApp({Key? key}) : super(key: key);
// This widget is the root of the application.
#override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Demo Company',
theme: ThemeData(),
debugShowCheckedModeBanner: false,
home: const HomePage(title: 'Demo Company'),
);
}
}
class _HomePageState extends State<HomePage> {
#override
initState() {
super.initState();
}
Widget _infoTile(String title, String subtitle) {
return ListTile(
title: Text(title),
subtitle: Text(subtitle.isEmpty ? 'Not set' : subtitle),
);
}
#override
Widget build(BuildContext context) {
return Scaffold(
drawer: const NavDrawer(),
appBar: AppBar(
title: Text(widget.title),
),
body: Center(
child: Column(
children: <Widget>[
_infoTile('App name', 'Demo App....'),
// Multiple Liste Tiles...
],
),
),
);
}
}
//----------------------------------------------------------------------
// navigation.dart
//----------------------------------------------------------------------
class NavDrawer extends StatelessWidget {
const NavDrawer({Key? key}) : super(key: key);
#override
Widget build(BuildContext context) {
return Drawer(
child: ListView(
padding: EdgeInsets.zero,
children: <Widget>[
DrawerHeader(
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: const <Widget>[
Text(
'Navigation',
style: TextStyle(color: Colors.white, fontSize: 30),
),
SizedBox(height: 30.0),
Text('Firstname', style: TextStyle(color: Colors.black, fontSize: 15)),
Text('Accountname', style: TextStyle(color: Colors.black, fontSize: 15)),
],
),
),
ListTile(
leading: const Icon(Icons.notifications),
title: const Text('Demo'),
onTap: () {
Navigator.push(
context,
Demo.route(),
);
},
),
// Multiple Navigation List Tiles...
],
),
);
}
}
//----------------------------------------------------------------------
// demo.dart
//----------------------------------------------------------------------
class HomePage extends StatefulWidget {
const HomePage({Key? key, required this.title}) : super(key: key);
final String title;
#override
State<HomePage> createState() => _HomePageState();
}
class Demo extends StatefulWidget {
const Demo({Key? key}) : super(key: key);
static Route route() {
return CupertinoPageRoute(builder: (_) => const Demo());
}
#override
_DemoState createState() => _DemoState();
}
class _DemoState extends State<Demo> {
final _data = <WordPair>[];
#override
void initState() {
super.initState();
_data.addAll(generateWordPairs().take(20));
}
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: const Text('Woolha.com Flutter Tutorial'),
),
body: _buildList(),
);
}
Widget _buildList() {
return RefreshIndicator(
onRefresh: _refreshData,
child: ListView.builder(
padding: const EdgeInsets.all(20.0),
itemBuilder: (context, index) {
WordPair wordPair = _data[index];
return _buildListItem(wordPair.asString, context);
},
itemCount: _data.length,
),
);
}
Widget _buildListItem(String word, BuildContext context) {
return Card(
child: Padding(
padding: const EdgeInsets.all(16.0),
child: Text(word),
),
);
}
Future _refreshData() async {
await Future.delayed(const Duration(seconds: 3));
_data.clear();
_data.addAll(generateWordPairs().take(20));
setState(() {});
}
}
class ShowMessages extends StatelessWidget {
final String type;
final Color color;
const ShowMessages({Key? key, required this.type, required this.color}) : super(key: key);
#override
Widget build(BuildContext context) {
return ListView(
//color: color,
physics: const AlwaysScrollableScrollPhysics(),
children: [
ListTile(
title: Text(
type,
style: Theme.of(context).textTheme.bodyText1,
),
),
]);
}
}
Copy this code to DartPad
What is wrong?
Well for me this code... works
I copied it into Dartpad, then Dev Tools in browser (F12) > Device Emulation > Responsive. And you can use pull to refresh.
Of course this doesn't work using web view and mouse. I believe this gesture is not supported.
I have a problem with my app...
I want only pass two 'double' arguments to widget in others pages when user using ElevatedButton and recover arguments for set coordonate in Maps.
I tried all the ways to do it by reading the doc on Flutter.dev but nothing the value I get is Null...
Main.dart :
import 'package:flutter/material.dart';
import 'package:booki3/route/route.dart' as route;
void main() {
runApp(const MyApp());
}
class MyApp extends StatelessWidget {
const MyApp({Key? key}) : super(key: key);
// This widget is the root of your application.
#override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Booking',
theme: ThemeData(
primarySwatch: Colors.blue,
),
onGenerateRoute: route.controller,
initialRoute: route.home,
);
}
}
Home.dart :
import 'package:flutter/material.dart';
import 'package:google_fonts/google_fonts.dart';
import 'package:booki3/views/maps.dart';
import 'package:booki3/route/route.dart' as route;
const dgreen = Color(0xFF54D3C2);
class HomePage extends StatelessWidget {
const HomePage({Key? key}) : super(key: key);
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: const MyAppBar(),
body: SingleChildScrollView(
child: Column(
children: [
const SearchSection(),
HotelSection(),
],
),
));
}
}
class Data {
double coordx = 45.20;
double coordy = 20.50;
}
class MyAppBar extends StatelessWidget implements PreferredSizeWidget {
const MyAppBar({Key? key}) : super(key: key);
#override
Size get preferredSize => const Size.fromHeight(50);
#override
Widget build(BuildContext context) {
return AppBar(
leading: IconButton(
icon: Icon(
Icons.arrow_back,
color: Colors.grey[800],
size: 20,
),
onPressed: null,
),
title: Text(
'Explore',
style: GoogleFonts.nunito(
color: Colors.black,
fontSize: 22,
fontWeight: FontWeight.w800,
),
),
centerTitle: true,
actions: [
IconButton(
icon: Icon(
Icons.favorite_outline_rounded,
color: Colors.grey[800],
size: 20,
),
onPressed: null,
),
IconButton(
icon: Icon(
Icons.place,
color: Colors.grey[800],
size: 20,
),
onPressed: () {
Navigator.push(
context,
MaterialPageRoute(
builder: (context) => const MyMaps(data: Data),
),
);
},
),
],
backgroundColor: Colors.white,
);
}
}
Maps.dart :
Line 25, I put random values because otherwise the page won't open... In the end, I want to put the values of Data. But so far I can't get them back.
import 'package:booki3/views/home.dart';
import 'package:flutter/material.dart';
import 'package:google_maps_flutter/google_maps_flutter.dart';
class MyMaps extends StatefulWidget {
const MyMaps({Key? key, required data}) : super(key: key);
#override
_MyAppState createState() => _MyAppState();
}
class _MyAppState extends State<MyMaps> {
late GoogleMapController mapController;
void _onMapCreated(GoogleMapController controller) {
mapController = controller;
}
#override
Widget build(BuildContext context) {
final data = ModalRoute.of(context)!.settings.arguments as Data;
debugPrint(data.toString());
LatLng _center = const LatLng(25.32, 2.5); // <= Two 'double' of Data..
return MaterialApp(
home: Scaffold(
appBar: AppBar(
title: const Text('Maps Sample App'),
backgroundColor: Colors.green[700],
),
body: GoogleMap(
onMapCreated: _onMapCreated,
initialCameraPosition: CameraPosition(
target: _center,
zoom: 11.0,
),
),
),
);
}
}
Route.dart :
import 'package:flutter/material.dart';
import 'package:booki3/views/home.dart';
import 'package:booki3/views/maps.dart';
const String home = "home";
const String maps = "maps";
Route<dynamic> controller(RouteSettings settings) {
switch (settings.name) {
case home:
return MaterialPageRoute(builder: (context) => const HomePage());
case maps:
return MaterialPageRoute(
builder: (context) => const MyMaps(
data: Data,
),
settings: const RouteSettings(
arguments: Data,
),
);
default:
throw ('This route name not exist');
}
}
With solution's Daniel, I have this error message :
Error Message
New Home.dart :
import 'package:flutter/material.dart';
import 'package:google_fonts/google_fonts.dart';
import 'package:booki3/views/maps.dart';
import 'package:booki3/route/route.dart' as route;
const dgreen = Color(0xFF54D3C2);
class HomePage extends StatelessWidget {
const HomePage({Key? key}) : super(key: key);
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: const MyAppBar(),
body: SingleChildScrollView(
child: Column(
children: [
const SearchSection(),
HotelSection(),
],
),
));
}
}
class Data {
double coordx = 45.20;
double coordy = 20.50;
#override
String toString() => 'Data(coordx: $coordx, coordy: $coordy)'; // just to prin
}
class MyAppBar extends StatelessWidget implements PreferredSizeWidget {
const MyAppBar({Key? key}) : super(key: key);
#override
Size get preferredSize => const Size.fromHeight(50);
#override
Widget build(BuildContext context) {
return AppBar(
leading: IconButton(
icon: Icon(
Icons.arrow_back,
color: Colors.grey[800],
size: 20,
),
onPressed: null,
),
title: Text(
'Explore',
style: GoogleFonts.nunito(
color: Colors.black,
fontSize: 22,
fontWeight: FontWeight.w800,
),
),
centerTitle: true,
actions: [
IconButton(
icon: Icon(
Icons.favorite_outline_rounded,
color: Colors.grey[800],
size: 20,
),
onPressed: null,
),
IconButton(
icon: Icon(
Icons.place,
color: Colors.grey[800],
size: 20,
),
onPressed: () {
Navigator.of(context).pushNamed(
route.maps,
arguments: Data,
);
},
),
],
backgroundColor: Colors.white,
);
}
}
New Route.dart :
import 'package:flutter/material.dart';
import 'package:booki3/views/home.dart';
import 'package:booki3/views/maps.dart';
const String home = "home";
const String maps = "maps";
Route<dynamic> controller(RouteSettings settings) {
final args = settings.arguments; // get the arguments here
switch (settings.name) {
case home:
return MaterialPageRoute(builder: (context) => const HomePage());
case maps:
return MaterialPageRoute(
builder: (context) => MyMaps(
data: args as Data,
),
);
default:
throw ('This route name not exist');
}
}
New Maps.dart :
import 'package:booki3/views/home.dart';
import 'package:flutter/material.dart';
import 'package:google_maps_flutter/google_maps_flutter.dart';
class MyMaps extends StatefulWidget {
const MyMaps({
Key? key,
required this.data,
}) : super(key: key);
final Data data;
#override
_MyAppState createState() => _MyAppState();
}
class _MyAppState extends State<MyMaps> {
late GoogleMapController mapController;
void _onMapCreated(GoogleMapController controller) {
mapController = controller;
}
#override
Widget build(BuildContext context) {
final data = widget.data;
debugPrint(data.toString());
LatLng _center = LatLng(data.coordx, data.coordy);
return MaterialApp(
home: Scaffold(
appBar: AppBar(
title: const Text('Maps Sample App'),
backgroundColor: Colors.green[700],
),
body: GoogleMap(
onMapCreated: _onMapCreated,
initialCameraPosition: CameraPosition(
target: _center,
zoom: 11.0,
),
),
),
);
}
}
Thank you in advance for your help because I don't know what to do anymore.. I feel like I have tried everything..
Love to you ;)
Ok, let's go step by step, in the Data class I only put the toString so that when you print it the values are displayed (nothing revealing).
The problem comes when you want to send ALL the class to the page Maps which is not possible (in this case), what you have to send is an instance of that class, therefore we create it.
On the other hand you will use pushNamed since you yourself are telling it that they are called "home", or "maps" in the routes, so we are going to use them, not to create another MaterialPageRoute if they are already in your routes, you got it?
Home :
class Data {
double coordx = 45.20;
double coordy = 20.50;
#override
String toString() => 'Data(coordx: $coordx, coordy: $coordy)'; // just to print
}
class MyAppBar extends StatelessWidget implements PreferredSizeWidget {
const MyAppBar({Key? key}) : super(key: key);
#override
Size get preferredSize => const Size.fromHeight(50);
#override
Widget build(BuildContext context) {
final newData = Data(); // new instance creation
return AppBar(
leading: IconButton(
icon: Icon(
Icons.arrow_back,
color: Colors.grey[800],
size: 20,
),
onPressed: null,
),
title: const Text(
'Explore',
style: TextStyle(
color: Colors.black,
fontSize: 22,
fontWeight: FontWeight.w800,
),
),
centerTitle: true,
actions: [
IconButton(
icon: Icon(
Icons.favorite_outline_rounded,
color: Colors.grey[800],
size: 20,
),
onPressed: null,
),
IconButton(
icon: Icon(
Icons.place,
color: Colors.grey[800],
size: 20,
),
onPressed: () {
Navigator.of(context).pushNamed( // using pushNamed not push
"maps",
arguments: newData, // send the instance
);
},
),
],
backgroundColor: Colors.white,
);
}
}
Routes :
Route<dynamic> controller(RouteSettings settings) {
final args = settings.arguments; // get the arguments here
switch (settings.name) {
case home:
return MaterialPageRoute(builder: (context) => const HomePage());
case maps:
return MaterialPageRoute(
builder: (context) => MyMaps( // we delete the settings and pass directly in the MyMaps
data: args as Data,
),
);
default:
throw ('This route name not exist');
}
}
Finally, once the instance is created, then sent by the arguments to the routes and finally arriving here, to obtain that instance, we simply add the final variable and in its constructor.
And the only thing left to do is to put it in your LatLng ! :D
Maps :
class MyMaps extends StatefulWidget {
const MyMaps({
Key? key,
required this.data, // here in constructor
}) : super(key: key);
final Data data; // final variable
#override
_MyAppState createState() => _MyAppState();
}
class _MyAppState extends State<MyMaps> {
late GoogleMapController mapController;
void _onMapCreated(GoogleMapController controller) {
mapController = controller;
}
#override
Widget build(BuildContext context) {
final data = widget.data; // get the data that comes
debugPrint(data.toString());
LatLng _center = LatLng(
data.coordx,
data.coordy,
); // voila !
return MaterialApp(
home: Scaffold(
appBar: AppBar(
title: const Text('Maps Sample App'),
backgroundColor: Colors.green[700],
),
body: GoogleMap(
onMapCreated: _onMapCreated,
initialCameraPosition: CameraPosition(
target: _center,
zoom: 11.0,
),
),
),
);
}
}
To support null, you need to convert
final data = ModalRoute.of(context)!.settings.arguments as Data;
to
final data = ModalRoute.of(context)!.settings.arguments as Data?;
As in the codes I mentioned below, my question is actually simple, but I couldn't find a simple answer on the internet. All the sources I found are going through the same example. There is no simple explanation, but there is good stackoverflow. Let me ask my question without further ado.
I can specify a variable in getx and print that variable on other pages. What I want to do now is I want to change the getx variable in the main file, how can I do that?
I'm posting the wrong version of the code I want to do below for you to understand.
code in getx folder
class numcontroller extends GetxController {
var derece = 20.obs;
}
code is second page
numcontroller deneme = Get.put(numcontroller());
Container(
margin: const EdgeInsets.fromLTRB(27, 10, 0, 0),
child: Row(
children: [
Container(
margin: const EdgeInsets.fromLTRB(5, 0, 0, 0),
child: Text('${deneme.derece.value}',
style: const TextStyle(
fontSize: 45,
fontFamily: 'YesevaOne',
color: Color(0xFF2d4b70)),
),
),
The code I want to run in main.dart
derece = 20
or
derece = 30
When I change the degree manually on main.dart, I want it to change on the second page as well.
EDİTİNG
import 'package:flutter/material.dart';
import 'package:get/get.dart';
import 'package:teemapp4/Controller/switch_controller.dart';
import 'routes/app_pages.dart';
import 'routes/app_routes.dart';
import 'themes/app_theme.dart';
//0xFF2d4b70
void main() {
runApp(const MyApp());
}
class MyApp extends StatelessWidget {
const MyApp({Key? key}) : super(key: key);
#override
Widget build(BuildContext context) {
return GetMaterialApp(
initialRoute: AppRoutes.DASHBOARD,
getPages: AppPages.list,
debugShowCheckedModeBanner: false,
theme: AppTheme.light,
darkTheme: AppTheme.dark,
themeMode: ThemeMode.system,
);
}
}
this is my main.dart code but i am using a bottombar i made with getx. I'm looking for how to change the data in that file through this code.
I don't think So you need to update your main.dart file.
You can add a button on your first page to update values like:
firstPage.dart
class FirstPage extends StatelessWidget {
FirstPage({Key? key}) : super(key: key);
NumController numController = Get.put(NumController());
#override
Widget build(BuildContext context) {
return SafeArea(
child: Scaffold(
body: Column(
children: [
ElevatedButton(
onPressed: () {
numController.updateDerece(30);
},
child: Text(
"Update Value",
),
),
ElevatedButton(
onPressed: () {
Get.to(() => SecondPage());
},
child: Text("Go To Second Screen"),
),
],
),
),
);
}
}
secondPage.dart
class SecondPage extends StatelessWidget {
SecondPage({Key? key}) : super(key: key);
NumController numController = Get.find<NumController>();
#override
Widget build(BuildContext context) {
return Container(
child: Text(
numController.derece.toString(),
),
);
}
}
Or You can directly update the value on your second page like:
secondPage.dart
class SecondPage extends StatelessWidget {
SecondPage({Key? key}) : super(key: key);
NumController numController = Get.put(NumController());
#override
Widget build(BuildContext context) {
return SafeArea(
child: Scaffold(
body: Column(
children: [
ElevatedButton(
onPressed: () {
//Any Number You can pass in Function
numController.updateDerece(30);
},
child: Text(
"Update Value",
),
),
Obx(
() => Container(
child: Text(
numController.derece.toString(),
),
),
),
],
),
),
);
}
}
numController.dart
import 'package:get/get.dart';
class NumController extends GetxController {
var _derece = 20.obs;
int get derece => _derece.value;
void updateDerece(int value) {
_derece.value = value;
}
}
Try using this way. And update your derece variable value using updateDerece method.
var _derece = 20.obs;
double get derece => _derece.value;
void updateDerece(double value) {
_derece.value = value;
}
////
Obx(() {
return Container(
margin: const EdgeInsets.fromLTRB(27, 10, 0, 0),
child: Row(
children: [
Container(
margin: const EdgeInsets.fromLTRB(5, 0, 0, 0),
child: Text(
'${deneme.derece}',
style: const TextStyle(
fontSize: 45,
fontFamily: 'YesevaOne',
color: Color(0xFF2d4b70)),
),
),
],
),
);
})
I am displaying the weight of an instance of a person class on my homepage. When I update the weight of this instance through a form in a popup bottom sheet the displayed weight is only changed after a hot reload. How can I trigger a setState in my person class when its instances parameters are changed in homepage?
main.dart
import 'package:flutter/material.dart';
import 'package:metricwidget/screens/homepage.dart';
void main() {
runApp(const MyApp());
}
class MyApp extends StatelessWidget {
const MyApp({Key? key}) : super(key: key);
// Root of application
#override
Widget build(BuildContext context) {
return MaterialApp(
debugShowCheckedModeBanner: false,
title: 'Flutter Demo',
theme: ThemeData(
primarySwatch: Colors.blue,
),
home: const Homepage(),
);
}
}
person.dart
import 'package:flutter/material.dart';
class person extends StatefulWidget {
int? weight;
person({Key? key, this.weight}) : super(key: key);
void updateWeight(newWeight){
weight = newWeight;
}
#override
_personState createState() => _personState();
}
class _personState extends State<person> {
#override
Widget build(BuildContext context) {
return Center(
child: Text(
widget.weight.toString(),
style: const TextStyle(fontSize: 24),
),
);
}
}
homepage.dart
import 'package:mvs/person.dart';
import 'package:flutter/material.dart';
class Homepage extends StatefulWidget {
const Homepage({Key? key}) : super(key: key);
#override
_HomepageState createState() => _HomepageState();
}
class _HomepageState extends State<Homepage> {
var joe = person(weight: 23);
final GlobalKey<FormState> _formKey = GlobalKey<FormState>();
#override
Widget build(BuildContext context) {
return Material(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Container(
child: joe,
),
OutlinedButton(
onPressed: () {
showModalBottomSheet(
context: context,
builder: (context) {
return Form(
key: _formKey,
child: Column(
children: [
Padding(
padding: const EdgeInsets.all(12.0),
child: TextFormField(
onSaved: (String? value) {
if (int.parse(value!) > 0) {
setState(() {
joe.updateWeight(int.parse(value));
});
}
},
keyboardType: TextInputType.number,
maxLength: 3,
initialValue: joe.weight.toString(),
decoration: const InputDecoration(
icon: Icon(Icons.label),
),
validator: (value) {
if (value!.isEmpty) {
return "Please enter value";
}
return null;
},
),
),
OutlinedButton(
onPressed: () {
_formKey.currentState!.save();
Navigator.pop(context);
},
child: const Text("submit"),
)
],
),
);
},
);
},
child: const Text("Update"),
)
],
),
);
}
}
Was able to solve this using provider and changenotifier, same as the format outlined in the docs below
Reference: https://pub.dev/packages/provider