Open bybabek opened 11 months ago
@bybabek
SideMenuData(
header: MenuHeaderWidget(
controller: _sideMenuController
),
items: [
SideMenuItemDataTile(
title: 'Dashboard',
isSelected: false,
titleStyle: TextStyle(color: Colors.white, fontWeight: FontWeight.w100),
onTap: () => _pageController.jumpToPage(0),
icon: const Icon(Icons.dashboard_outlined, color: Colors.white),
margin: const EdgeInsetsDirectional.only(
top: 30
),
),
SideMenuItemDataTile(
title: 'Investments',
isSelected: false,
titleStyle: TextStyle(color: Colors.white, fontWeight: FontWeight.w100),
onTap: () => _pageController.jumpToPage(1),
icon: const Icon(Icons.stacked_bar_chart_outlined, color: Colors.white)
),
SideMenuItemDataAccordion(
isCollapsed: _sideMenuController.isCollapsed(),
controller: _sideMenuAccordionController,
items: [
SideMenuItemDataTile(
title: 'Sub menu',
titleStyle: TextStyle(color: Colors.white),
isSelected: false,
onTap: (){},
)
]
),
]
)
class SideMenuAccordionController extends ChangeNotifier {
bool _isOpened;
SideMenuAccordionController({bool isInitiallyOpened = false})
: _isOpened = isInitiallyOpened;
bool get isOpened => _isOpened;
void open() {
if (!_isOpened) {
_isOpened = true;
notifyListeners();
}
}
void close() {
if (_isOpened) {
_isOpened = false;
notifyListeners();
}
}
void toggle() {
_isOpened = !_isOpened;
notifyListeners();
}
}
class SideMenuItemDataAccordion extends SideMenuItemDataDivider {
final List<SideMenuItemData> items;
final bool isCollapsed;
final SideMenuAccordionController controller;
SideMenuItemDataAccordion({
required this.items,
required this.isCollapsed,
required this.controller,
}) : super(divider: SizedBox()) {
if (isCollapsed) controller.close();
}
@override
Widget get divider => AnimatedBuilder(
animation: controller,
builder: (context, child) {
return Container(
decoration: BoxDecoration(
color: controller.isOpened ? const Color(0xff1b1b1b) : Colors.transparent,
borderRadius: const BorderRadius.all(Radius.circular(10)),
),
child: Column(
children: [
ListTile(
title: !isCollapsed
? const Text(
'My Submenu',
style: TextStyle(color: Colors.white, fontSize: 14),
maxLines: 1,
softWrap: true,
textScaler: TextScaler.noScaling,
overflow: TextOverflow.fade,
)
: null,
leading: const Icon(Icons.monetization_on_outlined, color: Colors.white),
contentPadding: const EdgeInsets.symmetric(horizontal: 10),
trailing: expandControlWidget,
),
subItemsWidget,
],
),
);
},
);
Widget? get expandControlWidget {
if (!isCollapsed) {
return IconButton(
icon: Icon(controller.isOpened ? Icons.expand_less : Icons.expand_more),
onPressed: controller.toggle,
);
}
return null;
}
Widget get subItemsWidget {
if (controller.isOpened && !isCollapsed) {
return Column(
children: items.map((subItem) {
if (subItem is SideMenuItemDataTile) {
return Padding(
padding: const EdgeInsets.symmetric(horizontal: 33),
child: SideMenuTile(item: subItem),
);
} else if (subItem is SideMenuItemDataTitle) {
return Padding(
padding: subItem.padding,
child: Text(
subItem.title,
style: subItem.titleStyle,
textAlign: subItem.textAlign,
),
);
} else if (subItem is SideMenuItemDataDivider) {
return Padding(
padding: subItem.padding,
child: subItem.divider,
);
}
return SizedBox.shrink();
}).toList(),
);
}
return SizedBox();
}
}
class SideMenuTile extends StatelessWidget {
final SideMenuItemDataTile item;
const SideMenuTile({Key? key, required this.item}) : super(key: key);
@override
Widget build(BuildContext context) {
return ListTile(
title: Text(item.title ?? "",
style: TextStyle(color: Colors.white, fontSize: 14),
maxLines: 1,
softWrap: true,
textScaler: TextScaler.noScaling,
overflow: TextOverflow.fade),
leading: item.icon,
onTap: item.onTap,
selected: item.isSelected,
titleTextStyle: item.titleStyle,
);
}
}
Is Accordion menu possible with this library?