Beautiful responsive navigation that automatically adapts between ConvexAppBar (mobile) and NavigationRail (desktop) based on screen size.
- 📱 Adaptive Layout: Automatically switches between mobile and desktop navigation
- 🎨 Beautiful Design: Convex bottom bar on mobile, rail navigation on desktop
- 🔔 Smart Badges: Hide when viewing, reappear when needed, clear permanently
- 🎯 Multiple Styles: fixed, fixedCircle, react, reactCircle, textIn, titled, flip
- 🌈 Full Customization: Colors, gradients, elevation, corner radius, and more
- ⚡ High Performance: Smooth animations, no lag
- 🌍 Cross-Platform: iOS, Android, Web, Desktop (Windows, macOS, Linux)
Mobile (< 600px): ConvexAppBar at bottom Desktop (≥ 600px): NavigationRail on side
[Add screenshots/GIFs here]
Add to your pubspec.yaml:
dependencies:
adaptive_navigation: ^1.0.0import 'package:adaptive_navigation/adaptive_navigation.dart';
import 'package:flutter/material.dart';
class MyApp extends StatefulWidget {
@override
State<MyApp> createState() => _MyAppState();
}
class _MyAppState extends State<MyApp> {
int _selectedIndex = 0;
@override
Widget build(BuildContext context) {
return MaterialApp(
home: AdaptiveConvexNavigation(
selectedIndex: _selectedIndex,
onTap: (index) => setState(() => _selectedIndex = index),
items: const [
TabItem(icon: Icons.home, title: 'Home'),
TabItem(icon: Icons.search, title: 'Search'),
TabItem(icon: Icons.person, title: 'Profile'),
],
child: _buildContent(),
),
);
}
Widget _buildContent() {
return Center(child: Text('Page $_selectedIndex'));
}
}That's it! Your app now has adaptive navigation! 🎉
class _MyAppState extends State<MyApp> {
int _selectedIndex = 0;
final Map<int, dynamic> _badges = {1: '5', 2: '99+'};
Map<int, dynamic> get _visibleBadges {
final visible = Map.from(_badges);
visible.remove(_selectedIndex); // Hide badge for active tab
return visible;
}
@override
Widget build(BuildContext context) {
return AdaptiveConvexNavigation.badge(
_visibleBadges,
selectedIndex: _selectedIndex,
onTap: (index) => setState(() => _selectedIndex = index),
badgeColor: Colors.red,
badgeTextColor: Colors.white,
items: const [
TabItem(icon: Icons.home, title: 'Home'),
TabItem(icon: Icons.message, title: 'Messages'),
TabItem(icon: Icons.notifications, title: 'Alerts'),
],
child: _buildContent(),
);
}
}AdaptiveConvexNavigation(
selectedIndex: _selectedIndex,
onTap: _handleTap,
breakpoint: 800, // Custom breakpoint
// Mobile styling
convexStyle: TabStyle.react,
backgroundColor: Colors.deepPurple,
activeColor: Colors.white,
gradient: LinearGradient(colors: [Colors.purple, Colors.blue]),
// Desktop styling
railBackgroundColor: Colors.deepPurple,
railLabelType: NavigationRailLabelType.all,
items: const [...],
child: MyContent(),
)- Getting Started - Quick start guide
- Usage Guide - Complete usage examples
- API Reference - Full API documentation
- Publishing Guide - For contributors
Perfect for:
- 📱 Mobile apps that need tablet support
- 💻 Web apps with desktop layouts
- 🌐 Cross-platform apps (iOS, Android, Web, Desktop)
- 📧 Messaging and social media apps with notifications
- 🛒 E-commerce apps with cart badges
- 📊 Dashboard apps with multiple views
No need for manual LayoutBuilder or responsive code. The widget handles everything:
// Before: Manual responsive code (30+ lines)
LayoutBuilder(
builder: (context, constraints) {
if (constraints.maxWidth >= 600) {
return Row([NavigationRail(...), Content()]);
} else {
return Scaffold(body: Content(), bottomNavigationBar: ConvexAppBar(...));
}
},
)
// After: One widget (10 lines)
AdaptiveConvexNavigation(
selectedIndex: _selectedIndex,
onTap: _handleTap,
items: [...],
child: Content(),
)Badges hide when you're viewing that tab, reappear when you navigate away:
- Click Messages → badge hides (you're viewing it)
- Click Home → Messages badge reappears (still unread)
- Click "Clear" → badge disappears permanently
- iOS: Smooth animations, respects safe areas
- Android: Material Design guidelines
- Web: Responsive at all breakpoints
- Desktop: Professional navigation rail
- ✅ TabController integration for PageView/TabBarView
- ✅ Custom chip builders for advanced badge designs
- ✅ Event blocking with onTapNotify
- ✅ Corner radius support (fixed styles)
- ✅ Gradient backgrounds
- ✅ Custom breakpoints
- ✅ Independent mobile/desktop styling
AdaptiveConvexNavigation- Main adaptive widgetConvexAppBar- Beautiful bottom navigation barTabItem- Navigation item configurationChipBuilder- Badge customization- Multiple tab styles and themes
Contributions are welcome! Please read the contributing guidelines first.
Apache License 2.0
Original ConvexAppBar by Chaobin Wu
AdaptiveConvexNavigation and additional features by contributors
Based on the original convex_bottom_bar package.
Made with ❤️ for the Flutter community