DropdownButton is not changing the value on onChanged - dart

The DropdownButton is not changing the value of dropdown after another selection is made from the dropdown. Below is my code.
Flexible(
child: Padding(
padding: EdgeInsets.fromLTRB(0.0, 0.0, 10.0, 0.0),
child: DropdownButton(
hint: Text('Select'),
items: list_dropdown,
onChanged: (val) {
setState(() {
wd = val;
});
},
value: wd,
)),
)
In the initState I'm setting the value variable
#override
void initState() {
// TODO: implement initState
super.initState();
wd = 0;
}
while I create the variale in the global scope
int wd;
Where am I going wrong?

Why did you create a variable in the global scope? If you want to mutate your variable called wd with setState(), you have to put it in your state class.
class App extends StatefulWidget {
#override
_AppState createState() => _AppState();
}
class _AppState extends State<App> {
// Here wd in my state class
int wd = 0;
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text("Cat Attack"),
),
body: Center(
child: DropdownButton(
value: wd,
onChanged: (val) {
setState(() {
wd = val;
});
},
items: [
DropdownMenuItem(
child: Text('1'),
value: 1,
),
DropdownMenuItem(
child: Text('2'),
value: 2,
),
],
),
));
}
}
You can override the value of wd in initState(), once you've defined in state.
class _AppState extends State<App> {
int wd;
#override
void initState() {
super.initState();
wd = 2;
}
Keep in mind that, your "value" for DropdownButton should be set to 'null' or be one from the values list. So if you set it to 5, rather then 1, 2 or null, which are the values in my DropdownMenuItem's, you will get this error:
I/flutter (15227): ══╡ EXCEPTION CAUGHT BY WIDGETS LIBRARY ╞═══════════════════════════════════════════════════════════
I/flutter (15227): The following assertion was thrown building App(dirty, state: _AppState#30354):
I/flutter (15227): 'package:flutter/src/material/dropdown.dart': Failed assertion: line 560 pos 15: 'items == null ||
I/flutter (15227): items.isEmpty || value == null || items.where((DropdownMenuItem item) => item.value ==
I/flutter (15227): value).length == 1': is not true.

Related

DropdownButton error after selection (HTTP-JSON-FutureBuilder)

I have some FutureBuilder that returns a DrobdownButton filled with the result of a HTTP request, using JSON response. I get the DropdownButton filled and everything seems to work just fine. The problem is after selecting an element I got an error:
'package:flutter/src/material/dropdown.dart': Failed assertion: line 609 pos 15: 'items == null ||
I/flutter ( 5210): items.isEmpty || value == null || items.where((DropdownMenuItem item) => item.value ==
I/flutter ( 5210): value).length == 1': is not true.
I understand that, for some reason, the DropdownButton get empty after selection or so...
I tried this code:
https://inducesmile.com/google-flutter/how-to-populate-dropdownbutton-using-json-api-in-flutter/
But in this case, after selection, the selected value goes to another widget. The thing I want is to use de value: parameter of the DropdownButton.
In the code above, the value: parameter is commented. I tried this code with no comment on that line and remove the SizedBox. The only thing I want is that the value is selected on the same DropdownButton
import 'dart:async';
import 'dart:io';
import 'package:flutter/material.dart';
void main() => runApp(MyApp());
class MyApp extends StatelessWidget {
#override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Demo',
theme: ThemeData(
primarySwatch: Colors.blue,
),
home: MyHomePage(title: 'Flutter Demo Home Page'),
);
}
}
class MyHomePage extends StatefulWidget {
MyHomePage({Key key, this.title}) : super(key: key);
final String title;
#override
_MyHomePageState createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
Items _currentItem;
Future<List<Items>> _getItemsData() async {
List<Items> dataItems = new List<Items>();
for (int i = 1; i <= 3; i++) {
dataItems.add(
Items.fromJson(
{'id':i,'name':'Elem ${i}'}
)
);
}
sleep(new Duration(seconds: 5));
return dataItems;
}
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text(widget.title),
),
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
new FutureBuilder(
future: _getItemsData(),
builder: (BuildContext context, AsyncSnapshot<List<Items>> snapshot) {
if (!snapshot.hasData) {
return CircularProgressIndicator();
} else {
return new Container(
width: 280,
child: new DropdownButton<Items>(
items: snapshot.data.map((items) => DropdownMenuItem<Items>(
child: Text(items.name),
value: items,
)).toList(),
onChanged: (Items value) {
setState(() {
_currentItem = value;
});
},
isExpanded: true,
value: _currentItem,
hint: Text('Select one...')
)
);
}
}
)
]
)
)
);
}
}
class Items {
int id;
String name;
Items({this.id, this.name});
factory Items.fromJson(Map<String, dynamic> json) {
return Items (
id: json['id'],
name: json['name']
);
}
}

Flutter how to update text on dropdownbutton when using Sqflite to populate the list

I have no problem populating the list from Sqflite database on DropdownButton. My only problem is updating the text once it's selected. It kept showing 'Airport' and I'm still learning to work with Object instead of String. I just couldn't figure that out.
Here's the code:
String selectedAirport;
AirportModel _currentAirport;
...
children: <Widget>[
FutureBuilder<List<AirportModel>>(
future: db.getAllAirports(),
builder: (BuildContext context, AsyncSnapshot<List<AirportModel>> snapshot) {
if (!snapshot.hasData) return CircularProgressIndicator();
return DropdownButton<AirportModel>(
items: snapshot.data
.map((airportItem) =>
DropdownMenuItem<AirportModel>(
value: airportItem,
child: Text(airportItem.airportName),
))
.toList(),
onChanged: (AirportModel value) {
setState(() {
_currentAirport = value;
selectedAirport = _currentAirport.airportName;
});
},
hint: Text("Airport"),
);
}),
DropdownButton has a property value. use it like value=_currentAirport
return DropdownButton<AirportModel>(
value:_currentAirport,
items: snapshot.data
.map((airportItem) =>
DropdownMenuItem<AirportModel>(
value: airportItem,
child: Text(airportItem.airportName),
))
.toList(),
onChanged: (AirportModel value) {
setState(() {
_currentAirport = value;
selectedAirport = _currentAirport.airportName;
});
},
hint: Text("Airport"),
);
Maybe items didn't reach yet or empty when value is set to DropdownButton. is _currentAirport initialized to some other value already?
Can you try like this? Also check if the items list are empty
items: snapshot.data == null ? null : _currentAirport
You can declare a Future and init in initState and in FutureBuilder use this future.
AirportModel _currentAirport;;
Future _future;
#override
void initState() {
_future = db.getAllAirports();
super.initState();
}
body: FutureBuilder<List<AirportModel>>(
future: _future,
You can use stream builder. Please check the example below.
class DropDownMenu extends StatefulWidget {
#override
_DropDownMenuState createState() => _DropDownMenuState();
}
class _DropDownMenuState extends State<DropDownMenu> {
var _currentSelectedValue;
final _dbHelper = DatabaseHelper.instance;
LoginPageManager _loginPageManager = new LoginPageManager();
final ValueNotifier<List<DropdownMenuItem<String>>> _dropDownMenuItems =
ValueNotifier<List<DropdownMenuItem<String>>>([]);
#override
void initState() {
_updateList();
super.initState();
}
#override
Widget build(BuildContext context) {
return Container(
alignment: Alignment.center,
width: 300,
height: 50,
margin: const EdgeInsets.only(top: 00.0),
child: ValueListenableBuilder(
builder: (BuildContext context, List<DropdownMenuItem<String>> list,
Widget child) {
return Container(
child: DropdownButton<String>(
hint: Text("Please Select a Server"),
value: _currentSelectedValue,
onChanged: (value) {
setState(() {
_currentSelectedValue = value;
});
},
items: list),
);
},
valueListenable: _dropDownMenuItems,
),
);
}
_updateList() async {
print("Update server has been called");
_dropDownMenuItems.value.clear();
List<Map<String, dynamic>> x = await _dbHelper.queryAllRows();
_dropDownMenuItems.value.add(_getAddServerButton());
x.forEach((element) {
_dropDownMenuItems.value.add(_getDropDownWidget(element));
});
}
DropdownMenuItem<String> _getDropDownWidget(Map<String, dynamic> map) {
int id = map['yxz'];
String text =
map['xyz'];
String value = map['zyx'];
return DropdownMenuItem<String>(
value: value,
child: Container(
width: 270,
child: Row(
children: [_getText(text), _getRemoveButton(id), _getEditButton(id)],
),
));
}
}
To make sure api data is not null:
child: _identity1 != null
? DropdownButtonFormField<dynamic>(
validator: (value) => value == null ? 'field required' : null

Flutter DropdownButton is Failed

I have created two DropdownButtons in the appBar and in the Body of a Scaffold.The Top DropdownButton changes the language whenever it is selected.After I selected One Conversion rate from the second Dropdown Button and Change the Language, the code crushes.Here is the Code..
import 'package:flutter/material.dart';
void main() => runApp(new MyApp());
class MyApp extends StatelessWidget {
#override
Widget build(BuildContext context) {
return new MaterialApp(
title: 'Flutter Demo',
theme: new ThemeData(
primarySwatch: Colors.blue),
home: new MyHomePage(title: 'Flutter Demo Home Page'),
);
}
}
class MyHomePage extends StatefulWidget {
MyHomePage({Key key, this.title}) : super(key: key);
final String title;
#override
_MyHomePageState createState() => new _MyHomePageState();
}
class User {
User(this.name);
final String name;
}
class CurrencyClass {
final String currencyType;
CurrencyClass(this.currencyType);
}
class _MyHomePageState extends State<MyHomePage> {
User selectedUser;
CurrencyClass selectedCurrency;
List<User> users = <User>
[User('English'),User('Amharic'),User('Oromigna'),
User('Tigrigna'),User('Somali')];
List<CurrencyClass> currency = <CurrencyClass>[
CurrencyClass('USD'),
CurrencyClass('GBP'),
CurrencyClass('CAD'),
CurrencyClass('AUD'),
CurrencyClass('EURO'),CurrencyClass('SAR'),];
#override
void initState() {
super.initState();
selectedUser = users[0];
}
#override
Widget build(BuildContext context) {
return new Scaffold(
appBar: new AppBar(
title: new Text(widget.title),
actions: <Widget>[
DropdownButton<User>(
value: selectedUser,
onChanged:(User newValue){
setState(() {
selectedUser = newValue;
if(newValue == users[0]){
currency = <CurrencyClass>[CurrencyClass('English'),CurrencyClass('CAD'),CurrencyClass('AUD'),CurrencyClass('EURO'),CurrencyClass('SAR')];
}
else if(newValue == users[1]){
currency = <CurrencyClass>[CurrencyClass('Amharic'),CurrencyClass('CAD'),CurrencyClass('AUD'),CurrencyClass('EURO'),CurrencyClass('SAR')];
}
else if(newValue == users[2]){
currency = <CurrencyClass>[CurrencyClass('Oromigna'),CurrencyClass('CAD'),CurrencyClass('AUD'),CurrencyClass('EURO'),CurrencyClass('SAR')];
} else if(newValue == users[3]){
currency = <CurrencyClass>[CurrencyClass('Tigringa'),CurrencyClass('CAD'),CurrencyClass('AUD'),CurrencyClass('EURO'),CurrencyClass('SAR')];
} else {
currency = <CurrencyClass>[CurrencyClass('Somaligna'),CurrencyClass('CAD'),CurrencyClass('AUD'),CurrencyClass('EURO'),CurrencyClass('SAR')];
}
});
},
items: users.map((User user){
return new DropdownMenuItem<User>(
value: user,
child:Text(
user.name,
style: TextStyle(color: Colors.black),
),
);
}).toList(),
)
],
),
body: new Center(
child: new Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
new Padding(padding: EdgeInsets.symmetric(vertical: 50.0),),
new Row(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
Text('Amount',style: TextStyle(fontSize: 20.0),),
Padding(padding: EdgeInsets.symmetric(horizontal: 15.0)),
Text('Birr',style: TextStyle(fontSize: 24.0),),
Padding(padding: EdgeInsets.symmetric(horizontal: 15.0)),
DropdownButton<CurrencyClass>(
value: selectedCurrency,
onChanged: (CurrencyClass newExchange){
setState(() {
selectedCurrency = newExchange;
});
},
items: currency.map((CurrencyClass user2){
return DropdownMenuItem<CurrencyClass>(
value: user2,
child: Text(
user2.currencyType,
style: TextStyle(color: Colors.red),
),
);
}).toList(),
),
],
),
],
),
),
);
}
}
Here is the Error when I select the top DropdownButton after selecting some value in the bottom dropdownButton
Launching lib/main.dart on XT1068 in debug mode...
Built build/app/outputs/apk/debug/app-debug.apk.
I/FlutterActivityDelegate(11200): onResume setting current activity to
this
I/flutter (11200): ══╡ EXCEPTION CAUGHT BY WIDGETS LIBRARY
╞═══════════════════════════════════════════════════════════
I/flutter (11200): The following assertion was thrown building
MyHomePage(dirty, state: _MyHomePageState#3ce11):
I/flutter (11200): 'package:flutter/src/material/dropdown.dart': F
Failed assertion: line 481 pos 15: 'value == null ||
I/flutter (11200): items.where((DropdownMenuItem<T> item) =>
item.value == value).length == 1': is not true.
I/flutter (11200): Either the assertion indicates an error in the
framework itself, or we should provide substantially
I/flutter (11200): more information in this error message to help you
determine and fix the underlying cause.
The problem in the original post is when setting the currency values on selecting the bar dropdown. You need to also set the selectedCurrency.
selectedCurrency = currency[0];
Or do what Gunter did in the edit. Just do not change the currency dropdown so there is no problem at all.
onChanged:(User newValue){
setState(() {
selectedUser = newValue;
if(newValue == users[0]){
currency = <CurrencyClass>[CurrencyClass('English'),CurrencyClass('CAD'),CurrencyClass('AUD'),CurrencyClass('EURO'),CurrencyClass('SAR')];
}
else if(newValue == users[1]){
currency = <CurrencyClass>[CurrencyClass('Amharic'),CurrencyClass('CAD'),CurrencyClass('AUD'),CurrencyClass('EURO'),CurrencyClass('SAR')];
}
else if(newValue == users[2]){
currency = <CurrencyClass>[CurrencyClass('Oromigna'),CurrencyClass('CAD'),CurrencyClass('AUD'),CurrencyClass('EURO'),CurrencyClass('SAR')];
}
else if(newValue == users[3]){
currency = <CurrencyClass>[CurrencyClass('Tigringa'),CurrencyClass('CAD'),CurrencyClass('AUD'),CurrencyClass('EURO'),CurrencyClass('SAR')];
}
else {
currency = <CurrencyClass>[CurrencyClass('Somaligna'),CurrencyClass('CAD'),CurrencyClass('AUD'),CurrencyClass('EURO'),CurrencyClass('SAR')];
}
selectedCurrency = currency[0];
});
},

Dart / flutter: DropdownButton causes exception when value is changed

I have written a pretty extensive form using DropdownButton and TextField widgets. The concept is that I have a StatefulWidget, where the class of State<StatefulWidget> contains 2 methods that return the widget I want to build. This way I can easily access and use the entered data and pass it along a function to compose an e-mail out of them.
However, when I select an item from the options, the framework throws an exception during the rebuild. I put in some log functions, and it shows that the setState() method successfully saves the value to selectedValue variable.
Widget buildMultiChoiceInputRow(var label, List<String> values) {
final List<String> options = values.toList();
selection = options.first;
final dropDownMenuOptions = options.map((String value) {
return new DropdownMenuItem<String>(
value: value,
child: new Text(value),
);
}).toList();
return new Column(
children: <Widget>[
new Row(
children: <Widget>[
new Expanded(
child: new Container(
padding:
const EdgeInsets.only(left: 5.0, top: 2.0, right: 5.0),
child: new Text(label, style: commonInfoCardInfoTextBlack16Bold)),
),
],
),
new Row(
children: <Widget>[
new Expanded(
child: new Container(
padding: const EdgeInsets.only(left: 5.0, right: 5.0),
child: new DropdownButton(
value: selectedValue,
items: dropDownMenuOptions,
onChanged: (selection) {
setState(() {
selectedValue = selection;
switch (label) {
case labelVirtualAdoption:
tempAdoptionType =
composeMultiChoiceAnswer(label, selection);
print(selection);
print(selectedValue);
break;
case labelAskedAboutSpecies:
tempAskedAboutSpecies =
composeMultiChoiceAnswer(label, selection);
break;
case labelHouseOrFlat:
tempHouseOrFlat =
composeMultiChoiceAnswer(label, selection);
break;
....
default:
break;
}
});
}),
),
)
],
),
new Divider(color: Colors.transparent)
],
);
}
Here is the exception:
I/flutter (20998): The following assertion was thrown building AdoptionInput(dirty, state: AdoptionInputState#3cc80):
I/flutter (20998): 'package:flutter/src/material/dropdown.dart': Failed assertion: line 481 pos 15: 'value == null ||
I/flutter (20998): items.where((DropdownMenuItem<T> item) => item.value == value).length == 1': is not true.
And here is the stack, showing that the exception is thrown during the rebuild:
I/flutter (20998): #2 new DropdownButton (package:flutter/src/material/dropdown.dart)
I/flutter (20998): #3 AdoptionInputState.buildMultiChoiceInputRow (package:osszefogasaszanhuzokert/adoptionPageUtilities.dart:443:28)
I/flutter (20998): #4 AdoptionInputState.build (package:osszefogasaszanhuzokert/adoptionPageUtilities.dart:639:11)
I/flutter (20998): #5 StatefulElement.build (package:flutter/src/widgets/framework.dart:3730:27)
I/flutter (20998): #6 ComponentElement.performRebuild (package:flutter/src/widgets/framework.dart:3642:15)
I/flutter (20998): #7 Element.rebuild (package:flutter/src/widgets/framework.dart:3495:5)
I/flutter (20998): #8 BuildOwner.buildScope (package:flutter/src/widgets/framework.dart:2242:33)
The problem seems really similar to a former bug in flutter, but if I try to initialize the selection and selectedValue in initState(), the same exception will be thrown right as the form is built for the first time.
What am I missing here?
Your "value" for DropdownButton should be set to 'null' or or be one from the values list.
DropdownButton(
value: null,
isDense: true,
onChanged: (String newValue) {
// somehow set here selected 'value' above whith
// newValue
// via setState or reactive.
},
items: ['yellow', 'brown', 'silver'].map((String value) {
return DropdownMenuItem(
value: value,
child: Text(value),
);
}).toList(),
),
So for my example DropdownButton value should be set to null or be 'yellow' or 'brown' or 'silver'.
Extending above answer with the second case where I was stuck.
Your "value" for DropdownButton should be set to 'null' or be one from the values list.
Your 'values' should also be different in every item value.
for example: Avoid this
items.add(DropdownMenuItem(
value: 1.toString(),
child: Text(1.toString()),
));
items.add(DropdownMenuItem(
value: 1.toString(),
child: Text(1.toString()),
));
Avoid repeating the values.
A bit off time, but, the code worked when I passed null as the "value" but I was having this problem when I placed a value that was included on the "Items". The problem was that the "Items" had a duplicate value, so it seems that you should provide all different items in the list passed to the "Items".
here is the right way:
import 'package:flutter/material.dart';
class RegisterFragments extends StatefulWidget {
RegisterFragments({Key key, this.step}) : super(key: key);
final int step;
_RegisterFragmentsState createState() => _RegisterFragmentsState();
}
class _RegisterFragmentsState extends State<RegisterFragments> {
Map<String, bool> values = {"abc": false, "def": true, "ghi": false};
List<String> _do = ['One', 'Two', 'Free', 'Four'];
String _dropdownValue = 'One';
#override
Widget build(BuildContext context) {
switch (widget.step) {
case 0:
return buildDo();
break;
case 1:
return Container(
child: ListView.builder(
shrinkWrap: true,
itemCount: values.length,
itemBuilder: (BuildContext context, int index) {
switch (widget.step) {
case 0:
return buildDo();
break;
case 1:
return buildService(context, index);
break;
default:
return Container();
break;
}
},
),
);
break;
default:
return Container();
break;
}
}
Widget buildService(BuildContext context, int index) {
String _key = values.keys.elementAt(index);
return Container(
child: Card(
child: CheckboxListTile(
title: Text(_key),
onChanged: (bool value) {
setState(() {
values[_key] = value;
});
},
value: values[_key],
),
),
);
}
Widget buildDo() {
return DropdownButton<String>(
isExpanded: true,
hint: Text("Service"),
items: _do.map<DropdownMenuItem<String>>((String value) {
return DropdownMenuItem<String>(
value: value,
child: Text(value),
);
}).toList(),
onChanged: (String newValue) {
setState(() {
this._dropdownValue = newValue;
});
},
value: _dropdownValue,
);
}
}
list and dorpdown value
List<String> _do = ['One', 'Two', 'Free', 'Four'];
String _dropdownValue = 'One';
dropdown items
tems: _do.map<DropdownMenuItem<String>>((String value) {
return DropdownMenuItem<String>( **
value: value,
child: Text(value),
);
}).toList(),
onChanged: (String newValue) {
setState(() {
this._dropdownValue = newValue;
});
},
value: _dropdownValue,
Use var to declare variable instead of String. Now you don't need to set the default value to null.
var dropdownvalue;
DropdownButton<String>(
value: dropdownvalue,
icon: Icon(Icons.keyboard_arrow_down),
iconSize: 28,
elevation: 20,
onChanged: (String newval){
setState((){
dropdownvalue = newval;
});
},
items: <String>["Registration","Verification", "ArenaRun"]
.map<DropdownMenuItem<String>>((String value){
return DropdownMenuItem<String>(
value: value,
child: Text(value),
);
}).toList(),
),
I was doing a value.toString() and the null was being converted to "null"!

Flutter Camera plugin error - The getter 'height' was called on null

I'm working on a Camera app. I'm using the following Camera plugin - https://github.com/flutter/plugins/tree/master/packages/camera
Here is my working code -
import 'dart:async';
import 'package:flutter/material.dart';
import 'package:camera/camera.dart';
List<CameraDescription> cameras;
Future<Null> main() async {
cameras = await availableCameras();
runApp(new MaterialApp(
home: new CameraApp(),
));
}
class CameraApp extends StatefulWidget {
#override
_CameraAppState createState() => new _CameraAppState();
}
class _CameraAppState extends State<CameraApp> {
CameraController controller;
#override
void initState() {
super.initState();
controller = new CameraController(cameras[0], ResolutionPreset.medium);
controller.initialize().then((_) {
if (!mounted) {
return;
}
setState(() {});
});
}
#override
void dispose() {
controller?.dispose();
super.dispose();
}
#override
Widget build(BuildContext context) {
// camera widget
Widget cameraView = new Container(
child: new Row(children: [
new Expanded(
child: new Column(
children: <Widget>[
new AspectRatio(
aspectRatio: controller.value.aspectRatio,
child: new CameraPreview(controller)
)
]
),
)
])
);
return new Scaffold(
body: new Stack(
children: <Widget>[
(!controller.value.initialized) ? new Container() : cameraView,
// ---On top of Camera view add one mroe widget---
],
),
);
}
}
When I'm building the app I'm getting following errors...
I/flutter ( 2097): The following NoSuchMethodError was thrown building CameraApp(dirty, state: _CameraAppState#a0666):
I/flutter ( 2097): The getter 'height' was called on null.
I/flutter ( 2097): Receiver: null
I/flutter ( 2097): Tried calling: height
Even though you have the ternary operator inside the body of the Stack, you are creating the Widget cameraView regardless of whether it is going to be used - so it is being created whether controller.value.initialized is true or false. Adjust the code so that the CameraPreview tree is only built if it is needed, i.e. if initialized is true. For example:
#override
Widget build(BuildContext context) {
return new Scaffold(
body: new Stack(
children: <Widget>[
(!controller.value.initialized) ? new Container() : buildCameraView(),
// ---On top of Camera view add one mroe widget---
],
),
);
}
Widget buildCameraView() {
return new Container(
child: new Row(
children: [
new Expanded(
child: new Column(
children: <Widget>[
new AspectRatio(
aspectRatio: controller.value.aspectRatio,
child: new CameraPreview(controller),
),
],
),
),
],
),
);
}
As you suggest in your comment, you can move the ternary operator lower in your build tree, too, and replace just the AspectRatio with an empty Container.
if even after using this check (!controller.value.initialized) ? new Container() : cameraView,still you are getting error that "getter 'height' was called on null",
and the error message is poping on your app only for fraction of second, then it means you are initializing your camera controller in didChangeDependencies()...if yes then use this technique.
bool cameraInitialized = false;
#override
void didChangeDependencies() {
if (cameraInitialized == false) {
final ScreenArguments arguments =
ModalRoute.of(context).settings.arguments;
int cameraIndex = Provider.of<XYZ>(context)
.XX
.firstWhere((element) => element.id == arguments.XX`enter code here`Id)
.cameraIndex;
controller = new CameraController(
widget.cameras[cameraIndex], ResolutionPreset.medium);
controller.initialize().then((value) {
if (!mounted) {
return;
}
setState(() {});
});
setState(() {
cameraInitialized = true;
});
}
super.didChangeDependencies();
}

Resources