Why variable value is not refreshing in flutter? - flutter

The variable value is not refreshing in flutter(which I created outside the class). The following way I have added.So in button press am setting different value. So if I come back to that screen again it is not showing 1. May I know why it is happening?
int _currVal = 1;
class AskFragment extends StatefulWidget {
static const String routeName = "//";
static const
int currState = -1;
#override
HomeScreenState createState() => HomeScreenState();
}

To update the values, use Stateful Widget and initialise values inside that Widget only, for any updates in the values of variables mention that in setState((){}) method to notify the change in the values.
See this for documentation of stateful widgets
See this for documentation of setState((){}) method
setState(() { _myVariable = newValue });
Note:- Never initialise changing values in build method they will not get updated instead they will be reinitialised with same values again and again

Related

Need help removing favorites from SharedPreferences

Im recreating the Google Translate app for a school project. When you translate a text the user can save userInput and translation so that they can go back to se it. The problem with my code starts when the user wants to remove the previous saved translation. When the user presses StarButton the isStarred value changes and I want to delete this previously saved translation and userInput. The problem is that I need to get the index of where the user pressed StarButton and then send it to removeFromSharedPreferences(). I have tried multiple options and I will be grateful for every help.
Since there is no code provided i will assume that StarButton is a custom widget that you created. You could simply put an attribute index to its class and then pass it in the constructor. In this way, every time you initialize a StarButton, you're gonna pass and index that identifies its position.
class StarButton extends StatefulWidget {
final int index;
const StarButton ({ super.key, required this.index});
#override
State<StarButton> createState() => _StarButtonState();
}
class _StarButtonState extends State<StarButton> {
#override
Widget build(BuildContext context) {
return YourWidget();
}
}

How to update textiew text based on another variable in dart

I have the following code, shown below where every time I make changes to a text field, a function gets called, in my case doSomething(). However, I assumed that since I bound the value of the text to a variable, if that variable were to get updated, the textfield text would also update. This is not happening, and my question is, what would be the simplest way to make the textfield update its text every time the corresponding variable changes.
Edit: Just to clarify, I have no problem getting the doSomething() function to update other parts of the code, I am looking for the inverse where an external variable changes the text of the textfield
import 'package:flutter/material.dart';
class DynamicTextField extends StatefulWidget {
const DynamicTextField(
{
required this.value,
Key? key})
: super(key: key);
final double value;
#override
State<DynamicTextField> createState() =>
_DynamicTextFieldState(value);
}
class _DynamicTextFieldState extends State<DynamicTextField> {
_DynamicTextFieldState(this.value);
final double value;
late TextEditingController textChanged;
#override
void initState() {
textChanged = TextEditingController(text: value.toString());
super.initState();
}
#override
Widget build(BuildContext context) {
return TextField(
controller: textChanged,
onChanged: (text) {
doSomething();
},
);
}
}
you can change the TextField value with the textChanged controller you set to that widget.
String stringVariable = "some value";
textChanged.text = stringVariable;
you can then update the state with a normal SetState(() {}), and it should update the value in TextField
Your value is declared as final. Meaning it can only be set once. Try removing the final declaration.
I also see you’re also declaring the value variable twice, instead of referencing the original value variable.
The second declaration should be in the widgets build method & should = widget.value.
this will update the text everytime DynamicTextField get rebuild.
#override
void initState() {
textChanged = TextEditingController(text: widget.value.toString());
super.initState();
}
Depends how you use the DynamicTextField in another class. The life-cycle of StatefullWidget is call the initState once the widget initialize.

in flutter when I pass model class in one of the Tab screen I get error in main Bottom Navigation screen

What I need to pass in BottomNav where I have mentioned all my tabs?
This is More TAB where I want to pass my MODEL class in widget:-
class More extends StatefulWidget{
final UserData currentUser; //UserData is model class
More(this.currentUser,) ;
#override
_MoreState createState() => new _MoreState();
}
And this is BottomNav screen, where I have mentioned all my TAB (I have commented line next to More()where I get error):-
class _BottomNavState extends State<BottomNav> {
int _index = 0;
List<Widget> _items = [
Home(),
UserProfile(FirebaseAuth.instance.currentUser,imageList: [],currentIndex:0),
Notifications(),
Chat(),
More(), /// I get error(red line below More() that I need to pass something here. What is that? So, that I can call my model class in widget.
];
#override
Widget build(BuildContext context) {
You have to provide an UserData to your More stateful widget since you declared that the More widget is expecting a UserData as a parameter
Such as:
final myUserData = UserData();
//...
More(myUserData),
You have defined your constructor like this
More(this.currentUser);
Which makes the currentUser as a mandatory positional parameter at position 0.
So while using your class, you should compulsorily pass an object of UserData like this,
More(UserData());
But in case, it is not mandatory, then you need to change your constructor to this,
More({ this.currentUser });

Flutter navigator 2.0 force new state to be created

I'm using the new Pages and Router APIs from Flutter's Navigator 2.0
My issue is that I have pages A and B opened and then a deepLink is called to page A. So what I do is clear the list of pages used in the navigator and recreate the pages with a new page A.
But what happens in this moment is that Navigator reuses the same Page A that existed before and only updates its state and properties (of the widget).
I tried overriding the method canUpdate on Page (below) in order to tell that page that now it should be rebuild, but the issue is that the Page class is immutable, so it complains that I can't have a non-final variable on it.
class CustomPage<T> extends Page<T> {
final Widget child;
bool _pageCanBeUpdated = true;
CustomPage({#required this.child, Key key}) : super(key: key);
#override
Route<T> createRoute(BuildContext context) {
return MaterialPageRoute(
builder: (context) => child,
settings: this,
);
}
void shouldCleanPage() {
_pageCanBeUpdated = false;
}
#override
bool canUpdate(Page other) {
return _pageCanBeUpdated && super.canUpdate(other);
}
}
I was able to solve it in another way. Instead of overriding the canUpdate method, I created a different key for the page.
In my RouterDelegate I keep a "salt" variable as int _salt and whenever I need to clean the whole stack of pages, I increment this salt and add append to the key. This way it is different until the next time I have to recreate it all.
Salt: int _salt = 0;
Initially: [Page(ValueKey('home $_salt')), Page(ValueKey('invites $_salt'))]
Clean pages: []
Increment salt: _salt++
Recreate page with [Page(ValueKey('home $_salt')
It forces the recreation of the whole page instead of reusing the ones that already exist.

How to reach a variable of a class from another class in Flutter

I have a stateful widget which includes buttons. I'm keeping number of user taps in an int variable called "counter".
I have another widget which is my home screen. I have a Text on that screen. I need to show the number of taps on this Text dynamically. So when user taps the button on the first class, my Text on the second class must be updated.
What is the best way to pass the counter variable from first widget to second widget?
Added some code
Both of my classes are stateful widgets. So, I declared static int counter like these;
class AppListView extends StatefulWidget {
static int counter;
#override
_AppListViewState createState() => _AppListViewState();
}
Now I can reach counter from other class but can't reach from its own class. I mean I need to increase counter in that part but It says undefined.
class _AppListViewState extends State<AppListView> {
#override
Widget build(BuildContext context) {
return FlatButton(
onPressed: (){
counter++ (can't reach counter here)
}
You might want to make your desired variable static.
class Something {
static int counter;
}
Then you can use the variable in the other widget like so:
class StatefulWidget{
FlatButton(
onPressed: (){
Something.counter++; // This variable is your counter you mentioned earlier
}
);
}
Approach 1:
Create a ValueChanged from Parent Widget add pass to FirstWidget, when change couter -> call ValueChanged to send update to Parent Widget, Parent will update state for second Widget.
Approach 2:
Create a Stream from Parent Widget add pass to FirstWidget and Sencond Widget (using StreamBuilder to render widget). when change couter -> change value of Stream to update to Second Widget.
Update Demo:
Link DartPad
Simple, in your code just write "widget.counter" in child. In statefull widget to access parent variable, you have to use "widget.instace". In this case, "widget.counter" will let u access counter variable of the parent.
class AppListView extends StatefulWidget {
int counter;
#override
_AppListViewState createState() => _AppListViewState();
}
class _AppListViewState extends State<AppListView> {
#override
Widget build(BuildContext context) {
return FlatButton(
onPressed: (){
widget.counter++
}
Note: u don't need counter variable to be static as u can call it with widget.counter in child class
You should use the provider package to associate the object with Provider, not any widget. Wrap the counter inside a class and pass it to MultiProvider:
void main() {
runApp(
MultiProvider(
providers: [
Provider(create: (context) => Something()),
],
child: const MyApp(),
),
);
}
And then you can access it from your build methods in each widget by:
var something = Provider.of<Something>(context, listen: false);
something.value++;
I suggest one of the existing easy solutions to use a global library to share your application variables between classes :
Create a dart file named globals.dart
globals.dart :
library YOUR_PACKAGE_NAME.globals;
int x = 1 ;
class1 :
import 'package:YOUR_PACKAGE_NAME/globals.dart' as globals;
print(globals.x) ; //prints 1
globals.x= 2 ;
class2 :
import 'package:YOUR_PACKAGE_NAME/globals.dart' as globals;
print(globals.x) ; //prints 2
https://devbrains.tn/forum/question/how-to-call-variables-from-different-class-in-flutter#6