Flutter Employee Management App: Add, Show, Search, Update & Delete
Flutter Employee Management App
This Flutter project demonstrates a simple employee management system with login, navigation, and full CRUD operations (Add, Show, Search, Update, and Delete).
HomePage with Tabs
The first HomePage uses a DefaultTabController with five tabs: Add, Show, Search, Update, and Delete.
class HomePage extends StatelessWidget {
const HomePage({super.key});
@override
Widget build(BuildContext context) {
return DefaultTabController(
length: 5,
child: Scaffold(
appBar: AppBar(
title: const Text("Employee Management"),
bottom: const TabBar(
isScrollable: true,
tabs: [
Tab(text: "Add"),
Tab(text: "Show"),
Tab(text: "Search"),
Tab(text: "Update"),
Tab(text: "Delete"),
],
),
),
body: const TabBarView(
children: [
AddPage(),
ShowPage(),
SearchPage(),
UpdatePage(),
DeletePage(),
],
),
),
);
}
}Drawer Menu with Logout
This version of HomePage includes a navigation drawer with a header, several menu items, and a logout dialog that returns the user to the LoginPage.
class HomePage extends StatelessWidget {
const HomePage({super.key});
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(title: const Text("Home")),
drawer: Drawer(
child: ListView(
children: [
const DrawerHeader(
decoration: BoxDecoration(color: Colors.blue),
child: Center(
child: Text("Menu", style: TextStyle(color: Colors.white)),
),
),
const ListTile(title: Text("Profile")),
const ListTile(title: Text("Settings")),
const ListTile(title: Text("Help")),
const ListTile(title: Text("About")),
// LOGOUT
ListTile(
title: const Text("Logout"),
onTap: () {
showDialog(
context: context,
builder: (_) => AlertDialog(
title: const Text("Logout"),
content: const Text("Do you want to logout?"),
actions: [
TextButton(
onPressed: () => Navigator.pop(context),
child: const Text("Cancel"),
),
TextButton(
onPressed: () {
Navigator.pop(context);
Navigator.pushReplacement(
context,
MaterialPageRoute(builder: (_) => const LoginPage()),
);
},
child: const Text("OK"),
),
],
),
);
},
),
],
),
),
);
}
}Add Employee Page
The AddPage collects employee name, ID, salary, and several options: permanent status, remote work, full-time status, and gender. Data is saved into the shared employees list.
class AddPage extends StatefulWidget {
const AddPage({super.key});
@override
State createState() => _AddPageState();
}
class _AddPageState extends State {
TextEditingController name = TextEditingController();
TextEditingController id = TextEditingController();
TextEditingController salary = TextEditingController();
bool isPermanent = false;
bool isRemote = false;
bool isFullTime = false;
String gender = "Male";
void save() {
employees.add({
"name": name.text,
"id": id.text,
"salary": salary.text,
"type": isPermanent ? "Permanent" : "Temporary",
"remote": isRemote ? "Yes" : "No",
"fulltime": isFullTime ? "Yes" : "No",
"gender": gender,
});
name.clear();
id.clear();
salary.clear();
setState(() {});
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(title: const Text("Add")),
body: Center(
child: SizedBox(
width: 300,
child: SingleChildScrollView(
child: Column(
children: [
TextField(controller: name, decoration: const InputDecoration(labelText: "Name")),
TextField(controller: id, decoration: const InputDecoration(labelText: "ID")),
TextField(controller: salary, decoration: const InputDecoration(labelText: "Salary")),
CheckboxListTile(
title: const Text("Permanent"),
value: isPermanent,
onChanged: (v) => setState(() => isPermanent = v!),
),
CheckboxListTile(
title: const Text("Remote"),
value: isRemote,
onChanged: (v) => setState(() => isRemote = v!),
),
CheckboxListTile(
title: const Text("Full Time"),
value: isFullTime,
onChanged: (v) => setState(() => isFullTime = v!),
),
RadioListTile(
title: const Text("Male"),
value: "Male",
groupValue: gender,
onChanged: (v) => setState(() => gender = v.toString()),
),
RadioListTile(
title: const Text("Female"),
value: "Female",
groupValue: gender,
onChanged: (v) => setState(() => gender = v.toString()),
),
ElevatedButton(onPressed: save, child: const Text("Add")),
],
),
),
),
),
);
}
}Search Employee Page
The SearchPage looks up an employee by ID and displays their name and salary, or a message if no match is found.
class SearchPage extends StatefulWidget {
const SearchPage({super.key});
@override
State createState() => _SearchPageState();
}
class _SearchPageState extends State {
TextEditingController id = TextEditingController();
Map? result;
bool searched = false;
void search() {
searched = true;
result = null;
for (var e in employees) {
if (e["id"] == id.text) result = e;
}
setState(() {});
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(title: const Text("Search")),
body: Center(
child: SizedBox(
width: 300,
child: Column(
children: [
TextField(controller: id, decoration: const InputDecoration(labelText: "Enter ID")),
ElevatedButton(onPressed: search, child: const Text("Search")),
if (searched && result != null)
Text("Name: ${result!["name"]}, Salary: ${result!["salary"]}")
else if (searched)
const Text("Employee not found"),
],
),
),
),
);
}
}Login Page
The LoginPage checks a hard-coded username and password. Valid credentials open the HomePage; otherwise, an Invalid Login message appears.
class LoginPage extends StatelessWidget {
const LoginPage({super.key});
@override
Widget build(BuildContext context) {
TextEditingController user = TextEditingController();
TextEditingController pass = TextEditingController();
return Scaffold(
appBar: AppBar(title: const Text("Login")),
body: Center(
child: SizedBox(
width: 300,
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
TextField(
controller: user,
decoration: const InputDecoration(labelText: "Username"),
),
TextField(
controller: pass,
decoration: const InputDecoration(labelText: "Password"),
obscureText: true,
),
const SizedBox(height: 20),
ElevatedButton(
onPressed: () {
if (user.text == "admin" && pass.text == "12345") {
Navigator.pushReplacement(
context,
MaterialPageRoute(builder: (_) => const HomePage()),
);
} else {
ScaffoldMessenger.of(context).showSnackBar(
const SnackBar(content: Text("Invalid Login")),
);
}
},
child: const Text("Login"),
),
],
),
),
),
);
}
}Show Employees Page
The ShowPage lists every saved employee with their name, ID, and salary.
class ShowPage extends StatelessWidget {
const ShowPage({super.key});
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(title: const Text("Show")),
body: ListView.builder(
itemCount: employees.length,
itemBuilder: (_, i) => ListTile(
title: Text("Name: ${employees[i]["name"]}"),
subtitle: Text("ID: ${employees[i]["id"]}, Salary: ${employees[i]["salary"]}"),
),
),
);
}
}Delete Employee Page
The DeletePage removes all employees matching the entered ID.
class DeletePage extends StatelessWidget {
const DeletePage({super.key});
@override
Widget build(BuildContext context) {
TextEditingController id = TextEditingController();
return Scaffold(
appBar: AppBar(title: const Text("Delete")),
body: Center(
child: SizedBox(
width: 300,
child: Column(
children: [
TextField(controller: id, decoration: const InputDecoration(labelText: "Enter ID")),
ElevatedButton(
onPressed: () {
employees.removeWhere((e) => e["id"] == id.text);
Navigator.pop(context);
},
child: const Text("Delete"),
),
],
),
),
),
);
}
}Menu Page with Navigation Buttons
This page presents five buttons that push the Add, Show, Search, Update, and Delete pages onto the navigation stack.
body: Center(
child: SizedBox(
width: 300,
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
ElevatedButton(
onPressed: () => Navigator.push(context, MaterialPageRoute(builder: (_) => const AddPage())),
child: const Text("Add"),
),
ElevatedButton(
onPressed: () => Navigator.push(context, MaterialPageRoute(builder: (_) => const ShowPage())),
child: const Text("Show"),
),
ElevatedButton(
onPressed: () => Navigator.push(context, MaterialPageRoute(builder: (_) => const SearchPage())),
child: const Text("Search"),
),
ElevatedButton(
onPressed: () => Navigator.push(context, MaterialPageRoute(builder: (_) => const UpdatePage())),
child: const Text("Update"),
),
ElevatedButton(
onPressed: () => Navigator.push(context, MaterialPageRoute(builder: (_) => const DeletePage())),
child: const Text("Delete"),
),
],
),
),
),
);
}
}Bottom Navigation Home Page
This stateful HomePage uses a BottomNavigationBar to switch between the five employee pages.
class HomePage extends StatefulWidget {
const HomePage({super.key});
@override
State createState() => _HomePageState();
}
class _HomePageState extends State {
int index = 0;
final List pages = const [
AddPage(),
ShowPage(),
SearchPage(),
UpdatePage(),
DeletePage(),
];
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(title: const Text("Employee Management")),
body: pages[index],
bottomNavigationBar: BottomNavigationBar(
currentIndex: index,
type: BottomNavigationBarType.fixed,
onTap: (i) {
setState(() {
index = i;
});
},
items: const [
BottomNavigationBarItem(icon: Icon(Icons.add), label: "Add"),
BottomNavigationBarItem(icon: Icon(Icons.list), label: "Show"),
BottomNavigationBarItem(icon: Icon(Icons.search), label: "Search"),
BottomNavigationBarItem(icon: Icon(Icons.update), label: "Update"),
BottomNavigationBarItem(icon: Icon(Icons.delete), label: "Delete"),
],
),
);
}
}Update Employee Page
The UpdatePage finds an employee by ID and updates their name and salary.
class UpdatePage extends StatelessWidget {
const UpdatePage({super.key});
@override
Widget build(BuildContext context) {
TextEditingController id = TextEditingController();
TextEditingController name = TextEditingController();
TextEditingController salary = TextEditingController();
return Scaffold(
appBar: AppBar(title: const Text("Update")),
body: Center(
child: SizedBox(
width: 300,
child: Column(
children: [
TextField(controller: id, decoration: const InputDecoration(labelText: "Enter ID")),
TextField(controller: name, decoration: const InputDecoration(labelText: "New Name")),
TextField(controller: salary, decoration: const InputDecoration(labelText: "New Salary")),
ElevatedButton(
onPressed: () {
for (var e in employees) {
if (e["id"] == id.text) {
e["name"] = name.text;
e["salary"] = salary.text;
}
}
Navigator.pop(context);
},
child: const Text("Update"),
),
],
),
),
),
);
}
}
English with a size of 14.65 KB