Sitemap

Generic Drop-down Flutter

2 min readFeb 15, 2024

--

Creating drop downs in flutter could be messy, need dozens of line of code, for just little difference between all of them “the Type” only, when we think about that we find it's worthless to repeat the same code and just change the type only, in this article we will discuss how to create only one drop down and use it across the application and by using that we will save the time and achieve specially when we need to write validation and extra code for each drop down, modularity in our application:

1-

first of all we are going to create base class that have string variable called name which we will pass to our drop down like the following:

abstract class DropAble {
final String name;
//each dorpable should over-ride the name in the constructor
DropAble({
required this.name,
});
}

2-

we need to create our drop down widget and it will be like

// we enforce here each T should be extends DropAble 
class GenericDropDown<T extends DropAble> extends StatelessWidget {
const GenericDropDown({
super.key,
required this.options,
required this.onChanged,
this.value
});
final List<T> options;
// callback function called when the user change the select another value
final void Function(T?) onChanged;
// the value of selected item
final T? value;

@override
Widget build(BuildContext context) {
return DropdownButton(
value: value,
items: options
.map((e) => DropdownMenuItem<T?>(value: e, child: Text(e.name,),),)
.toList(),
onChanged:(value) => onChanged(value),
);
}
}

3-

now we are going to create an example

// in my case i choosed to create drop down for Employees 
class Employee extends DropAble{
Employee({required String name}) : super(name: name);
int age = 20;
double salary = 2000;
String phoneNumber = '123456789';
}
// here is another model for our example

class Device extends DropAble{
Device({required String name}) : super(name: name);
double price = 2000;
String manufacturer = 'Samsung';
String os = 'Android';
}
// and here is the full example
void main() {
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 MaterialApp(
title: 'Flutter Demo',
theme: ThemeData(
colorScheme: ColorScheme.fromSeed(seedColor: Colors.deepPurple),
useMaterial3: true,
),
home: Column(
children: [
GenericDropDown(
options: [
Employee(name: 'ayman'),
Employee(name: 'aly'),
Employee(name: 'mohammed'),
Employee(name: 'omara'),
], onChanged: (employee ) {
print(employee?.age);
print(employee?.salary);
},
),
GenericDropDown(
options: [
Device(name: 'iphone 15 pro max'),
Device(name: 'iphone 14 pro max'),
Device(name: 'iphone 13 pro'),
Device(name: 'iphone 12'),
], onChanged: (device ) {
print(device?.price);
print(device?.manufacturer);
print(device?.os);
},
)
]
),
);
}
}

as we can see above in this emaple we change the type of the drop down smoothly
and here is the github link for the project https://github.com/AymanOmara/drop_down_flutter

Get Aymanomara’s stories in your inbox

Join Medium for free to get updates from this writer.

my linked in account :https://www.linkedin.com/in/ayman-omara/

let me know if you liked the article

--

--