Ausgabe
Ich hoffe, es geht dir gut. Ich habe ein kleines Problem, ich möchte den Wert eines DropdownButton basierend auf dem Wert eines anderen DropdownButton dynamisch ändern.
Nun, ich werde erklären, wo ich stehe und was das Problem ist:
Zuerst habe ich eine Liste von StudyCycle mit 3 Elementen;
final _studyCycles = const <StudyCycle>[
StudyCycle(cycle: Cycles.elementary, classrooms: <ClassroomsLevels>[
ClassroomsLevels.cp,
ClassroomsLevels.ce1,
ClassroomsLevels.ce2,
ClassroomsLevels.cm1,
ClassroomsLevels.cm2,
]),
StudyCycle(cycle: Cycles.primary, classrooms: <ClassroomsLevels>[
ClassroomsLevels.sixth,
ClassroomsLevels.fifth,
ClassroomsLevels.fourth,
ClassroomsLevels.third,
]),
StudyCycle(cycle: Cycles.secondary, classrooms: <ClassroomsLevels>[
ClassroomsLevels.second,
ClassroomsLevels.first,
ClassroomsLevels.terminal,
])
];
Diese StudyCycle- Liste wird verwendet, um die erste Dropdown-Schaltfläche zu erstellen
DropdownButton<StudyCycle>(
value: _selectedStudyCycle,
items: List<DropdownMenuItem<StudyCycle>>.generate(
_studyCycles.length,
(index) => DropdownMenuItem<StudyCycle>(
value: _studyCycles[index],
child: Text(_studyCycles[index].cycle.toString()),
),
),
hint: const Text('Your Study Cycle'),
onChanged: (StudyCycle? studyCycle) {
if (studyCycle != _selectedStudyCycle) {
if (_selectedStudyCycle != null) setState(() => _selectedStudyCycle = null);
if (studyCycle != null) setState(() => _selectedStudyCycle = studyCycle);
}
},
)
Und durch Auswahl eines StudyCycle aus dem StudyCycles-Dropdown können Werte eines anderen Dropdown-Buttons erstellt werden, der diesmal die ClassroomsLevels des StudyCycle enthält, der derzeit im StudyCycles-Dropdown ausgewählt ist (so weit, so gut).
DropdownButton<ClassroomsLevels>(
hint: const Text('Select your classroom'),
value: _selectedClassroom,
items: _selectedStudyCycle == null
? []
: List<DropdownMenuItem<ClassroomsLevels>>.generate(
_selectedStudyCycle!.classrooms.length,
(index) => DropdownMenuItem<ClassroomsLevels>(
value: _selectedStudyCycle!.classrooms[index],
child: Text(_selectedStudyCycle!.classrooms[index].toString()),
),
),
onChanged: (ClassroomsLevels? classroom) => setState(() => _selectedClassroom = classroom),
)
Das Problem tritt auf, wenn ein ClassroomLevel ausgewählt ist und ich StudyCycle ändere, erhalte ich diesen Fehler:
There should be exactly one item with [DropdownButton]'s value: ClassroomsLevels.fourth.
Either zero or 2 or more [DropdownMenuItem]s were detected with the same value
'package:flutter/src/material/dropdown.dart':
Failed assertion: line 915 pos 15: 'items == null || items.isEmpty || value == null ||
items.where((DropdownMenuItem<T> item) {
return item.value == value;
}).length == 1'
Ich habe mein Bestes versucht, um das Problem zu lösen, aber ich konnte es nicht (und ich verstehe nicht wirklich warum), also verlasse ich mich auf Sie. Können Sie mir helfen, den Fehler zu verstehen und ihn zu beheben?
Der vollständige Code
import 'package:flutter/material.dart';
class MyHomePage2 extends StatefulWidget {
const MyHomePage2({Key? key, required this.title}) : super(key: key);
final String title;
@override
State<MyHomePage2> createState() => _MyHomePage2State();
}
class _MyHomePage2State extends State<MyHomePage2> {
final _studyCycles = const <StudyCycle>[
StudyCycle(cycle: Cycles.elementary, classrooms: <ClassroomsLevels>[
ClassroomsLevels.cp,
ClassroomsLevels.ce1,
ClassroomsLevels.ce2,
ClassroomsLevels.cm1,
ClassroomsLevels.cm2,
]),
StudyCycle(cycle: Cycles.primary, classrooms: <ClassroomsLevels>[
ClassroomsLevels.sixth,
ClassroomsLevels.fifth,
ClassroomsLevels.fourth,
ClassroomsLevels.third,
]),
StudyCycle(cycle: Cycles.secondary, classrooms: <ClassroomsLevels>[
ClassroomsLevels.second,
ClassroomsLevels.first,
ClassroomsLevels.terminal,
])
];
StudyCycle? _selectedStudyCycle;
ClassroomsLevels? _selectedClassroom;
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(title: Text(widget.title)),
body: SizedBox(
width: MediaQuery.of(context).size.width,
child: Column(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
crossAxisAlignment: CrossAxisAlignment.center,
children: [
DropdownButton<StudyCycle>(
value: _selectedStudyCycle,
items: List<DropdownMenuItem<StudyCycle>>.generate(
_studyCycles.length,
(index) => DropdownMenuItem<StudyCycle>(
value: _studyCycles[index],
child: Text(_studyCycles[index].cycle.toString()),
),
),
hint: const Text('Your Study Cycle'),
onChanged: (StudyCycle? studyCycle) {
if (studyCycle != _selectedStudyCycle) {
if (_selectedStudyCycle != null) setState(() => _selectedStudyCycle = null);
if (studyCycle != null) setState(() => _selectedStudyCycle = studyCycle);
}
},
),
//
DropdownButton<ClassroomsLevels>(
hint: const Text('Select your classroom'),
value: _selectedClassroom,
items: _selectedStudyCycle == null
? []
: List<DropdownMenuItem<ClassroomsLevels>>.generate(
_selectedStudyCycle!.classrooms.length,
(index) => DropdownMenuItem<ClassroomsLevels>(
value: _selectedStudyCycle!.classrooms[index],
child: Text(_selectedStudyCycle!.classrooms[index].toString()),
),
),
onChanged: (ClassroomsLevels? classroom) => setState(() => _selectedClassroom = classroom),
),
],
),
),
);
}
}
class StudyCycle {
final Cycles cycle;
final List<ClassroomsLevels> classrooms;
final String? description;
final int? iconCodePoint;
const StudyCycle({
required this.cycle,
required this.classrooms,
this.description,
this.iconCodePoint,
});
}
enum Cycles { elementary, primary, secondary, secondaryTechnique }
enum ClassroomsLevels {
cp,
ce1,
ce2,
cm1,
cm2,
sixth,
fifth,
fourth,
third,
second,
first,
terminal,
mechanical,
electronic,
electricity,
inEngineering,
secretariat,
accounting,
economy,
agr1,
agr2,
agr3,
}
DANKE!
Lösung
Der Grund für den Fehler ist, dass der Wert _selectedClassroom
in Ihrem zweiten Dropdown-Menü nicht in der neuen Klassenzimmerliste vorhanden ist, _selectedStudyCycle!.classrooms
sobald Sie den Wert des ersten Dropdown-Menüs ändern. Setzen Sie einfach den Wert Ihres zweiten Dropdowns in der setState
Methode zurück:
if (studyCycle != null) {
setState(() {
// Add this line
_selectedClassroom = null;
_selectedStudyCycle = studyCycle;
});
}
Beantwortet von – hnnngwdlch
Antwort geprüft von – Dawn Plyler (FixError Volunteer)