flutter_screenutil not working ,,,problem in builder - flutter

I am using flutter_screenutil: ^5.5.3+2
and build_runner: ^2.0.4
after running the build runner
there is error in the builder of screenutlils

use ScreenUtilInit like this
#override
Widget build(BuildContext context) {
// In first method you only need to wrap [MaterialApp] with [ScreenUtilInit] and that's it
return ScreenUtilInit(
builder: (_, child) {
return MaterialApp(
debugShowCheckedModeBanner: false,
title: 'Test',
theme: ThemeData(
primarySwatch: Colors.blue,
textTheme: TextTheme(bodyText2: TextStyle(fontSize: 30.sp)),
),
home: child,
);
},
child: HomePage(),
);
}
}

The issue is here ScreenUtilInit builder require context and child
builder: (context , child) { //this
Widget build(BuildContext context) {
return ScreenUtilInit(
builder: (context, child) {
return MultiBlocProvider(
providers: [],
child: Text("AA"),
);
},
);
}

Related

Could not find the correct Provider above the BlocListener Widget

I'm trying to use Bloc provider for user authentication in my flutter app. When I try to access the data i'm always getting this error even though I double checked all the files.
This is the error i'm getting:
Error: Could not find the correct Provider<StateStreamable<Object?>> above this
BlocListener<StateStreamable<Object?>, Object?> Widget
This happens because you used a `BuildContext` that does not include the provider
main.dart:
void main() async {
runApp(const MyApp());
}
class MyApp extends StatelessWidget {
const MyApp({super.key});
// This widget is the root of your application.
#override
Widget build(BuildContext context) {
return MultiBlocProvider(
providers: [
BlocProvider(
create: (context) => AuthBloc(LoginInitState(), AuthRepository()))
],
child: MaterialApp(
title: 'Flutter app',
debugShowCheckedModeBanner: false,
theme: ThemeData(
primarySwatch: Colors.blue,
visualDensity: VisualDensity.adaptivePlatformDensity),
home: const LoginPage(),
),
);
}
}
parts from login.dart:
#override
void initState() {
authBloc = BlocProvider.of<AuthBloc>(context);
super.initState();
}
######################################################
return Scaffold(
backgroundColor: Colors.grey[300],
body: BlocListener(
listener: (context, state) {
if (state is UserLoginSuccessState) {
Navigator.push(context,
MaterialPageRoute(builder: (context) => const HomeScreen()));
}
},
child: SafeArea...
I'm still new to flutter and struggling with the state management part, I'd be glad if anybody can help!
In your BlocListener you're missing the State and the Bloc
Here's what I mean
BlocListener<AuthBloc, AuthState>(
listener: (context, state) {
if (state is UserLoginSuccessState) {
Navigator.push(context,
MaterialPageRoute(builder: (context) => const HomeScreen()));
}
},
child: SafeArea...

I am building an android app using flutter code and i am facing this issue

I am deploying an app using flutter code in android studio everything is working perfect but i am new to flutter and i am facing this issue.
I have purchased this app code from some third party.
can you help me with this?
error: The argument type 'MaterialApp Function()' can't be assigned to the parameter type 'Widget Function(BuildContext, Widget)'. (argument_type_not_assignable at [infixedu] lib\main.dart:70)
#override
Widget build(BuildContext context) {
SystemChrome.setPreferredOrientations([
DeviceOrientation.portraitUp,
DeviceOrientation.portraitDown,
]);
return FutureBuilder(
future: Utils().checkService(),
builder: (context, snapshot) {
if (snapshot.connectionState == ConnectionState.done) {
if (snapshot.data == true) {
return isRTL != null
? isRTL
? ScreenUtilInit(
designSize: Size(360, 690),
builder: () => MaterialApp(
title: "infixEdu",
debugShowCheckedModeBanner: false,
theme: basicTheme(),
home: Stack(
children: [
FutureBuilder(
future: _initialization,
builder: (context, snapshot) {
if (snapshot.hasError) {
return Scaffold(
body: Center(
child: Text(
snapshot.error.toString(),
),
),
);
}
if (snapshot.connectionState ==
ConnectionState.done) {
return Scaffold(
body: Splash(),
);
}
return CircularProgressIndicator();
}),
],
),
localizationsDelegates: [
GlobalMaterialLocalizations.delegate,
GlobalWidgetsLocalizations.delegate,
GlobalCupertinoLocalizations.delegate,
],
supportedLocales: [
Locale("fa", "IR"),
// OR Locale('ar', 'AE') OR Other RTL locales
],
))
: ScreenUtilInit(
designSize: Size(360, 690),
builder: () => MaterialApp(
title: "InfixEdu",
debugShowCheckedModeBanner: false,
theme: basicTheme(),
home: Scaffold(
body: Splash(),
),
),
)
: ScreenUtilInit(
designSize: Size(360, 690),
builder: () => Material(
child: Directionality(
textDirection: TextDirection.ltr,
child: Center(
child: CupertinoActivityIndicator()))));
} else {
return MaterialApp(
debugShowCheckedModeBanner: false,
home: ErrorPage(),
);
}
}
return MaterialApp(
debugShowCheckedModeBanner: false,
home: Scaffold(body: Center(child: CupertinoActivityIndicator())),
);
});
}
}

Change the name route when user click widget - flutter web

I am declaring routes inside main.dart like this:
class MyApp extends StatelessWidget {
#override
Widget build(BuildContext context) {
return MaterialApp(
debugShowCheckedModeBanner: false,
theme: ThemeData(
primarySwatch: Colors.blue,
),
initialRoute: '/',
routes: {
'/': (context) => HomeScreen(isLogin: false),
'/home': (context) => Home(),
'/pageok': (context) => AnotherPage()
});
}
}
and I have custom side bar that I need to access in all pages that I have. Here is the way I define the side bar
#override
Widget build(BuildContext context) {
print(MediaQuery.of(context).size.width);
return Scaffold(
appBar: AppBarCustom(),
body: Stack(
children: <Widget>[
ValueListenableBuilder(
valueListenable: indexPage,
builder: (_, val, __) {
if (indexPage.value == 0)
return BerandaPelamar();
else if (indexPage.value == 1)
// Navigator.pushNamed(context, "/pageok"); ..... *****
return AnotherPage();
else
return Container(
color: Colors.red,
);
}),
//here is my custom side bar
ValueListenableBuilder(
valueListenable: indexPage,
builder: (_, val, __) {
return NavBarCustom(indexPage: indexPage);
})
],
));
}
So from ***** in my code I would like to return a Navigator that navigate user to a screen but I don't able to do that since I have to return a widget inside ValueListenableBuilder. Is there a way to do that or is there a way.. so that when user is in AnotherPage screen the route become http://localhost:59849/#/pageok

Flutter - losing Provider state on hot reload

When I hot-reload my app, I lose state from my Provider classes. I'm aware that Provider properly preserves state so I know the issue comes from my code, but I cannot figure out where I'm going wrong. I have the following:
main.dart
class App extends StatelessWidget {
#override
Widget build(BuildContext context) {
return FutureBuilder(
future: GlobalData.fetchTheme(),
builder: (BuildContext context, AsyncSnapshot<String> themeSnapshot) {
if (themeSnapshot.hasData) {
GlobalData.theme = themeSnapshot.data;
return Phoenix(
child: MaterialApp(
title: 'MyApp',
home: Scaffold(body: Root()),
theme: ThemeData(
accentColor: Palette.green
),
)
);
}
return Loading();
}
);
}
}
root.dart
class Root extends StatelessWidget {
#override
Widget build(BuildContext context) {
return StreamBuilder<FirebaseUser>(
stream: FireAuth().getInstance().onAuthStateChanged,
builder: (context, snapshot) {
if (snapshot.connectionState == ConnectionState.active) {
FirebaseUser user = snapshot.data;
if (user != null) {
GlobalData.setUid(user.uid);
}
return user == null ? Auth() : SafeArea(child: KeyboardDismisser(child: Core()));
} else {
return Loading();
}
},
);
}
}
core.dart
class Core extends StatelessWidget {
Widget build(BuildContext context) {
return Column(
children: <Widget>[
FutureBuilder(
future: Users.getUser(GlobalData.uid),
builder: (BuildContext context, AsyncSnapshot<TuneUser> userSnapshot) {
if (userSnapshot.hasData) {
return MultiProvider(
providers: [
ChangeNotifierProvider(create: (context) => UserProvider(userSnapshot.data)),
ChangeNotifierProvider(create: (context) => SearchProvider()),
ChangeNotifierProvider(create: (context) => DetailsProvider()),
],
child: Expanded(child: BottomBarNavigation())
);
}
return Expanded(child: Loading());
}
),
BottomBar()
]
);
}
}
I assume at some point I'm rebuilding or losing state when I shouldn't, I've tried a lot of things with the help of similar questions already present, but I can't seem to fix it.
Any ideas?
Would really appreciate the help.
Cheers,
Andy
wrap you MultiProvider in the main.dart
MultiProvider(
providers: [
ChangeNotifierProvider(create: (context) => UserProvider(userSnapshot.data)),
ChangeNotifierProvider(create: (context) => SearchProvider()),
ChangeNotifierProvider(create: (context) => DetailsProvider()),
],
child: child: MaterialApp(
title: 'MyApp',
home: Scaffold(body: Root()),
theme: ThemeData(
accentColor: Palette.green
),
),
),

Should every screen check for authentication before loading or should it be done only in the main.dart file?

This might be a very basic question but I wanted to understand the best practices followed around the industry.
Right now I am doing this in the build method of the main.dart file.
#override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Demo',
theme: ThemeData(
primarySwatch: Colors.green,
),
home: new StreamBuilder(
stream: auth.onAuthStateChanged,
builder: (context, snapshot) {
if (snapshot.hasData) {
return MainScreen();
}
return AuthScreen();
},
),
);
}
i don't think anything is wrong with this method, i also use something similar for restarting my app, however there is a problem. when you change the route and get unauthorized it won't open main screen ( because you are no longer in Home widget )
you can try these solutions :
use Builder:
#override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Demo',
theme: ThemeData(
primarySwatch: Colors.green,
),
home: MainScreen(),
builder: (context, widget) {
return StreamBuilder(
stream: auth.onAuthStateChanged,
builder: (context, snapshot) {
if (snapshot.hasData) {
return widget;
}
return AuthScreen();
},
),
},
);
}
it fixes the issue but you may have data in your widget that may be invalid due to Unauthentication so my suggestion is to restart app like this :
double appKey = 0;
#overrdie
initState() {
super.initState();
auth.onAuthStateChanged.listen(() {
setState(() { appKey++; });
});
}
#override
Widget build(BuildContext context) {
return MaterialApp(
key: Key('$appKey'),
title: 'Flutter Demo',
theme: ThemeData(
primarySwatch: Colors.green,
),
home: new StreamBuilder(
stream: auth.onAuthStateChanged,
builder: (context, snapshot) {
if (snapshot.hasData) {
return MainScreen();
}
return AuthScreen();
},
),
);
}
but if you are sure you handle invalid data it's better to listen to onAuthStateChanged ( like in code above ) and push AuthScreen via navigator and block user from exiting screen using WillPopScope widget in AuthScreen. It feels better because of transition animation.