import 'dart:convert'; import 'package:flutter/material.dart'; import 'package:provider/provider.dart'; import 'package:scrollable_positioned_list/scrollable_positioned_list.dart'; import 'package:sendtrain/extensions/string_extensions.dart'; import 'package:sendtrain/models/activity_timer_model.dart'; class ActivityActionView extends StatefulWidget { const ActivityActionView({super.key, required this.actions}); final List actions; @override State createState() => ActivityActionViewState(); } class ActivityActionViewState extends State { final ItemScrollController itemScrollController = ItemScrollController(); final ScrollOffsetController scrollOffsetController = ScrollOffsetController(); final ItemPositionsListener itemPositionsListener = ItemPositionsListener.create(); final ScrollOffsetListener scrollOffsetListener = ScrollOffsetListener.create(); @override Widget build(BuildContext context) { ActivityTimerModel atm = Provider.of(context, listen: true); List sets = json.decode(widget.actions[0].set); // we need to set the scroll controller // so we can update the selected item position atm.setScrollController(itemScrollController); return Expanded( child: ScrollablePositionedList.builder( padding: const EdgeInsets.fromLTRB(10, 0, 10, 20), itemCount: sets.length, itemScrollController: itemScrollController, scrollOffsetController: scrollOffsetController, itemPositionsListener: itemPositionsListener, scrollOffsetListener: scrollOffsetListener, itemBuilder: (BuildContext context, int setNum) { List content = []; List set = sets[setNum]; for (int actionNum = 0; actionNum < set.length; actionNum++) { Map setItem = set[actionNum]; content.add(GestureDetector( onTap: () { atm.setAction(setNum, actionNum, 'manual'); atm.setActionCount(); itemScrollController.scrollTo( index: setNum, duration: Duration(milliseconds: 500), curve: Curves.easeInOutCubic); }, child: Row(children: [ Ink( width: 70, padding: const EdgeInsets.all(15), color: atm.isCurrentItem(setNum, actionNum) ? Theme.of(context).colorScheme.primaryContainer : Theme.of(context).colorScheme.onPrimary, child: Text( textAlign: TextAlign.center, '${setNum + 1}.${actionNum + 1} ')), Expanded( child: Ink( padding: const EdgeInsets.all(15), color: atm.isCurrentItem(setNum, actionNum) ? Theme.of(context).colorScheme.surfaceBright : Theme.of(context).colorScheme.surfaceContainerLow, child: Text( textAlign: TextAlign.center, '${setItem['name']}: ${setItem['amount']} ${setItem['type']}'.toTitleCase()))) ]))); } if (setNum == 0) { return Card( shape: const RoundedRectangleBorder( borderRadius: BorderRadius.only( topLeft: Radius.circular(0), topRight: Radius.circular(0), bottomLeft: Radius.circular(10), bottomRight: Radius.circular(10)), ), clipBehavior: Clip.antiAlias, child: Column(children: content)); } else { return Card( shape: const RoundedRectangleBorder( borderRadius: BorderRadius.only( topLeft: Radius.circular(10), topRight: Radius.circular(10), bottomLeft: Radius.circular(10), bottomRight: Radius.circular(10)), ), clipBehavior: Clip.antiAlias, child: Column(children: content)); } // return Column(children: contents); }, )); } }