gt_dropdown 1.1.0
gt_dropdown: ^1.1.0 copied to clipboard
A highly customizable and feature-rich dropdown widget for Flutter, offering seamless integration with forms, validation, animations, and extensive styling options.#FlutterDropdown #CustomDropdown #Dr [...]
import 'package:flutter/material.dart';
import 'package:gt_dropdown/gt_dropdown.dart';
/// The main entry point of the Flutter application.
void main() {
runApp(const MyApp());
}
/// The root widget of the application.
class MyApp extends StatelessWidget {
const MyApp({super.key});
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'GT Dropdown Example',
debugShowCheckedModeBanner: false,
theme: ThemeData(
colorScheme: ColorScheme.fromSeed(seedColor: Colors.deepPurple),
useMaterial3: true,
),
home: const DropdownExamplePage(),
);
}
}
/// Example page demonstrating CustomDropdown features.
class DropdownExamplePage extends StatefulWidget {
const DropdownExamplePage({super.key});
@override
State<DropdownExamplePage> createState() => _DropdownExamplePageState();
}
class _DropdownExamplePageState extends State<DropdownExamplePage> {
// Selected values
String? selectedTheme;
Country? selectedCountry;
String? selectedLanguage;
bool hasSubmitted = false;
// Sample data
final List<String> themes = ['Light', 'Dark', 'Auto'];
final List<Country> countries = [
Country('United States', '🇺🇸'),
Country('India', '🇮🇳'),
Country('Japan', '🇯🇵'),
Country('Germany', '🇩🇪'),
Country('Brazil', '🇧🇷'),
];
final List<String> languages = [
'English',
'Spanish',
'French',
'German',
'Japanese',
'Chinese',
'Korean',
'Italian',
'Portuguese',
'Russian',
];
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: const Text('GT Dropdown Examples'),
backgroundColor: Colors.deepPurple,
foregroundColor: Colors.white,
),
body: ListView(
padding: const EdgeInsets.all(20),
children: [
// Example 1: Simple String Dropdown
_buildSection(
title: 'Simple String Dropdown',
description: 'Basic dropdown with string items',
child: CustomDropdown<String>(
items: themes,
initialSelection: selectedTheme,
itemBuilder: (context, item) => Text(item),
onSelected: (value) => setState(() => selectedTheme = value),
label: const Text('Theme'),
hintText: 'Choose a theme',
prefixIcon: const Icon(Icons.palette, size: 20),
),
),
const SizedBox(height: 24),
// Example 2: Model Class with Custom Layout
_buildSection(
title: 'Model Class Dropdown',
description: 'Dropdown using a model class with flag emoji',
child: CustomDropdown<Country>(
items: countries,
initialSelection: selectedCountry,
itemBuilder: (context, country) => Row(
children: [
Text(country.flag, style: const TextStyle(fontSize: 20)),
const SizedBox(width: 10),
Expanded(child: Text(country.name)),
],
),
onSelected: (value) => setState(() => selectedCountry = value),
label: const Text('Country'),
hintText: 'Select your country',
prefixIcon: const Icon(Icons.flag, size: 20),
borderRadius: 12,
),
),
const SizedBox(height: 24),
// Example 3: Dropdown with Validation
_buildSection(
title: 'Dropdown with Validation',
description: 'Shows validation message when no selection is made',
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
CustomDropdown<String>(
items: languages,
initialSelection: selectedLanguage,
itemBuilder: (context, item) => Text(item),
onSelected: (value) =>
setState(() => selectedLanguage = value),
label: const Text('Language'),
hintText: 'Select a language',
enableSearch: true,
menuHeight: 250,
validationMessage: hasSubmitted && selectedLanguage == null
? 'Please select a language'
: null,
prefixIcon: const Icon(Icons.language, size: 20),
),
const SizedBox(height: 12),
ElevatedButton(
onPressed: () => setState(() => hasSubmitted = true),
style: ElevatedButton.styleFrom(
backgroundColor: Colors.deepPurple,
foregroundColor: Colors.white,
),
child: const Text('Submit'),
),
],
),
),
const SizedBox(height: 24),
// Example 4: Custom Styling
_buildSection(
title: 'Custom Styled Dropdown',
description: 'Dropdown with custom colors and elevation',
child: CustomDropdown<String>(
items: const ['Low', 'Medium', 'High', 'Critical'],
itemBuilder: (context, item) => Row(
children: [
Icon(
_getPriorityIcon(item),
color: _getPriorityColor(item),
size: 18,
),
const SizedBox(width: 10),
Text(item),
],
),
onSelected: (value) {},
label: const Text('Priority Level'),
hintText: 'Set priority',
borderRadius: 16,
menuBackgroundColor: Colors.grey.shade100,
menuElevation: 8,
prefixIcon: const Icon(Icons.flag, size: 20),
),
),
const SizedBox(height: 24),
// Example 5: Disabled Dropdown
_buildSection(
title: 'Disabled Dropdown',
description: 'Dropdown in disabled state',
child: CustomDropdown<String>(
items: themes,
initialSelection: 'Dark',
itemBuilder: (context, item) => Text(item),
onSelected: (value) {},
enabled: false,
label: const Text('Locked Theme'),
hintText: 'Cannot be changed',
prefixIcon: const Icon(Icons.lock, size: 20),
),
),
const SizedBox(height: 20),
],
),
);
}
Widget _buildSection({
required String title,
required String description,
required Widget child,
}) {
return Container(
padding: const EdgeInsets.all(16),
decoration: BoxDecoration(
color: Colors.white,
borderRadius: BorderRadius.circular(12),
border: Border.all(color: Colors.grey.shade300),
boxShadow: [
BoxShadow(
color: Colors.black.withValues(alpha: 0.05),
blurRadius: 6,
offset: const Offset(0, 2),
),
],
),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Text(
title,
style: const TextStyle(
fontSize: 16,
fontWeight: FontWeight.bold,
color: Colors.deepPurple,
),
),
const SizedBox(height: 6),
Text(
description,
style: TextStyle(fontSize: 13, color: Colors.grey.shade700),
),
const SizedBox(height: 16),
child,
],
),
);
}
IconData _getPriorityIcon(String priority) {
switch (priority) {
case 'Low':
return Icons.arrow_downward;
case 'Medium':
return Icons.drag_handle;
case 'High':
return Icons.arrow_upward;
case 'Critical':
return Icons.priority_high;
default:
return Icons.flag;
}
}
Color _getPriorityColor(String priority) {
switch (priority) {
case 'Low':
return Colors.green;
case 'Medium':
return Colors.orange;
case 'High':
return Colors.red;
case 'Critical':
return Colors.purple;
default:
return Colors.grey;
}
}
}
// Model Classes
class Country {
final String name;
final String flag;
Country(this.name, this.flag);
@override
String toString() => name;
}