mirror of
https://github.com/wger-project/flutter.git
synced 2026-02-18 00:17:48 +01:00
Merge pull request #459 from 12people/ux_fixes
Removing Dismissible for better discoverability
This commit is contained in:
@@ -808,5 +808,11 @@
|
||||
"none__bodyweight_exercise_": "none (bodyweight exercise)",
|
||||
"@none__bodyweight_exercise_": {
|
||||
"description": "Generated entry for translation for server strings"
|
||||
}
|
||||
},
|
||||
"editSchedule": "Edit schedule",
|
||||
"log": "Log",
|
||||
"@log": {
|
||||
"description": "Log a specific meal"
|
||||
},
|
||||
"done": "Done"
|
||||
}
|
||||
|
||||
@@ -107,6 +107,7 @@ class NutritionalPlanScreen extends StatelessWidget {
|
||||
),
|
||||
],
|
||||
flexibleSpace: FlexibleSpaceBar(
|
||||
titlePadding: const EdgeInsets.fromLTRB(56, 0, 56, 16),
|
||||
title: Text(
|
||||
nutritionalPlan.getLabel(context),
|
||||
style: Theme.of(context).textTheme.titleLarge?.copyWith(color: appBarForeground),
|
||||
|
||||
@@ -82,6 +82,7 @@ class _WorkoutPlanScreenState extends State<WorkoutPlanScreen> {
|
||||
iconTheme: const IconThemeData(color: appBarForeground),
|
||||
backgroundColor: wgerPrimaryColor,
|
||||
flexibleSpace: FlexibleSpaceBar(
|
||||
titlePadding: const EdgeInsets.fromLTRB(56, 0, 56, 16),
|
||||
title: Text(
|
||||
workoutPlan.name,
|
||||
style: Theme.of(context).textTheme.titleLarge?.copyWith(color: appBarForeground),
|
||||
|
||||
@@ -146,14 +146,6 @@ class _DashboardNutritionWidgetState extends State<DashboardNutritionWidget> {
|
||||
return out;
|
||||
}
|
||||
|
||||
Widget getTrailing() {
|
||||
if (!_hasContent) {
|
||||
return const Text('');
|
||||
}
|
||||
|
||||
return _showDetail ? const Icon(Icons.expand_less) : const Icon(Icons.expand_more);
|
||||
}
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Card(
|
||||
@@ -174,7 +166,15 @@ class _DashboardNutritionWidgetState extends State<DashboardNutritionWidget> {
|
||||
Icons.restaurant,
|
||||
color: Theme.of(context).textTheme.headlineSmall!.color,
|
||||
),
|
||||
trailing: getTrailing(),
|
||||
trailing: _hasContent
|
||||
? Tooltip(
|
||||
message: AppLocalizations.of(context).toggleDetails,
|
||||
child: _showDetail
|
||||
? const Icon(
|
||||
Icons.info,
|
||||
)
|
||||
: const Icon(Icons.info_outline))
|
||||
: const SizedBox(),
|
||||
onTap: () {
|
||||
setState(() {
|
||||
_showDetail = !_showDetail;
|
||||
@@ -182,16 +182,18 @@ class _DashboardNutritionWidgetState extends State<DashboardNutritionWidget> {
|
||||
},
|
||||
),
|
||||
if (_hasContent)
|
||||
Column(
|
||||
children: [
|
||||
...getContent(),
|
||||
Container(
|
||||
padding: const EdgeInsets.all(15),
|
||||
height: 180,
|
||||
child: FlNutritionalPlanPieChartWidget(_plan!.nutritionalValues),
|
||||
)
|
||||
],
|
||||
)
|
||||
Padding(
|
||||
padding: const EdgeInsets.symmetric(horizontal: 10),
|
||||
child: Column(
|
||||
children: [
|
||||
...getContent(),
|
||||
Container(
|
||||
padding: const EdgeInsets.symmetric(horizontal: 5, vertical: 15),
|
||||
height: 180,
|
||||
child: FlNutritionalPlanPieChartWidget(_plan!.nutritionalValues),
|
||||
)
|
||||
],
|
||||
))
|
||||
else
|
||||
NothingFound(
|
||||
AppLocalizations.of(context).noNutritionalPlans,
|
||||
@@ -441,14 +443,6 @@ class _DashboardWorkoutWidgetState extends State<DashboardWorkoutWidget> {
|
||||
_hasContent = _workoutPlan != null;
|
||||
}
|
||||
|
||||
Widget getTrailing() {
|
||||
if (!_hasContent) {
|
||||
return const Text('');
|
||||
}
|
||||
|
||||
return _showDetail ? const Icon(Icons.expand_less) : const Icon(Icons.expand_more);
|
||||
}
|
||||
|
||||
List<Widget> getContent() {
|
||||
final List<Widget> out = [];
|
||||
|
||||
@@ -540,7 +534,15 @@ class _DashboardWorkoutWidgetState extends State<DashboardWorkoutWidget> {
|
||||
Icons.fitness_center,
|
||||
color: Theme.of(context).textTheme.headlineSmall!.color,
|
||||
),
|
||||
trailing: getTrailing(),
|
||||
trailing: _hasContent
|
||||
? Tooltip(
|
||||
message: AppLocalizations.of(context).toggleDetails,
|
||||
child: _showDetail
|
||||
? const Icon(
|
||||
Icons.info,
|
||||
)
|
||||
: const Icon(Icons.info_outline))
|
||||
: const SizedBox(),
|
||||
onTap: () {
|
||||
setState(() {
|
||||
_showDetail = !_showDetail;
|
||||
@@ -548,8 +550,8 @@ class _DashboardWorkoutWidgetState extends State<DashboardWorkoutWidget> {
|
||||
},
|
||||
),
|
||||
if (_hasContent)
|
||||
Container(
|
||||
padding: const EdgeInsets.only(left: 10),
|
||||
Padding(
|
||||
padding: const EdgeInsets.symmetric(horizontal: 10),
|
||||
child: Column(
|
||||
children: [
|
||||
...getContent(),
|
||||
|
||||
@@ -43,11 +43,18 @@ class MealWidget extends StatefulWidget {
|
||||
}
|
||||
|
||||
class _MealWidgetState extends State<MealWidget> {
|
||||
bool _expanded = false;
|
||||
bool _showingDetails = false;
|
||||
bool _editing = false;
|
||||
|
||||
void _toggleExpanded() {
|
||||
void _toggleEditing() {
|
||||
setState(() {
|
||||
_expanded = !_expanded;
|
||||
_editing = !_editing;
|
||||
});
|
||||
}
|
||||
|
||||
void _toggleDetails() {
|
||||
setState(() {
|
||||
_showingDetails = !_showingDetails;
|
||||
});
|
||||
}
|
||||
|
||||
@@ -57,85 +64,72 @@ class _MealWidgetState extends State<MealWidget> {
|
||||
padding: const EdgeInsets.all(3),
|
||||
child: Card(
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
DismissibleMealHeader(_expanded, _toggleExpanded, meal: widget._meal),
|
||||
if (_expanded)
|
||||
Row(
|
||||
mainAxisSize: MainAxisSize.max,
|
||||
mainAxisAlignment: MainAxisAlignment.spaceAround,
|
||||
children: [
|
||||
IconButton(
|
||||
onPressed: () {
|
||||
// Delete the meal
|
||||
Provider.of<NutritionPlansProvider>(context, listen: false)
|
||||
.deleteMeal(widget._meal);
|
||||
|
||||
// and inform the user
|
||||
ScaffoldMessenger.of(context).showSnackBar(
|
||||
SnackBar(
|
||||
content: Text(
|
||||
AppLocalizations.of(context).successfullyDeleted,
|
||||
textAlign: TextAlign.center,
|
||||
),
|
||||
),
|
||||
);
|
||||
},
|
||||
icon: const Icon(Icons.delete),
|
||||
),
|
||||
if (widget._meal.mealItems.isNotEmpty)
|
||||
Ink(
|
||||
decoration: ShapeDecoration(
|
||||
color: Theme.of(context).primaryColor, //wgerPrimaryButtonColor,
|
||||
shape: const CircleBorder(),
|
||||
),
|
||||
child: IconButton(
|
||||
icon: const Icon(Icons.history_edu),
|
||||
color: Colors.white,
|
||||
MealHeader(
|
||||
editing: _editing,
|
||||
toggleEditing: _toggleEditing,
|
||||
showingDetails: _showingDetails,
|
||||
toggleDetails: _toggleDetails,
|
||||
meal: widget._meal),
|
||||
if (_editing)
|
||||
Padding(
|
||||
padding: const EdgeInsets.symmetric(vertical: 8),
|
||||
child: Wrap(
|
||||
spacing: 8,
|
||||
children: [
|
||||
TextButton.icon(
|
||||
icon: const Icon(Icons.add),
|
||||
label: Text(AppLocalizations.of(context).addIngredient),
|
||||
onPressed: () {
|
||||
Provider.of<NutritionPlansProvider>(context, listen: false)
|
||||
.logMealToDiary(widget._meal);
|
||||
ScaffoldMessenger.of(context).showSnackBar(
|
||||
SnackBar(
|
||||
content: Text(
|
||||
AppLocalizations.of(context).mealLogged,
|
||||
textAlign: TextAlign.center,
|
||||
),
|
||||
Navigator.pushNamed(
|
||||
context,
|
||||
FormScreen.routeName,
|
||||
arguments: FormScreenArguments(
|
||||
AppLocalizations.of(context).addIngredient,
|
||||
MealItemForm(widget._meal, widget._listMealItems),
|
||||
hasListView: true,
|
||||
),
|
||||
);
|
||||
},
|
||||
),
|
||||
),
|
||||
IconButton(
|
||||
onPressed: () {
|
||||
Navigator.pushNamed(
|
||||
context,
|
||||
FormScreen.routeName,
|
||||
arguments: FormScreenArguments(
|
||||
AppLocalizations.of(context).edit,
|
||||
MealForm(widget._meal.planId, widget._meal),
|
||||
),
|
||||
);
|
||||
},
|
||||
icon: const Icon(Icons.edit),
|
||||
),
|
||||
],
|
||||
),
|
||||
if (_expanded) const Divider(),
|
||||
...widget._meal.mealItems.map((item) => MealItemWidget(item, _expanded)),
|
||||
OutlinedButton(
|
||||
child: Text(AppLocalizations.of(context).addIngredient),
|
||||
onPressed: () {
|
||||
Navigator.pushNamed(
|
||||
context,
|
||||
FormScreen.routeName,
|
||||
arguments: FormScreenArguments(
|
||||
AppLocalizations.of(context).addIngredient,
|
||||
MealItemForm(widget._meal, widget._listMealItems),
|
||||
hasListView: true,
|
||||
),
|
||||
);
|
||||
},
|
||||
),
|
||||
TextButton.icon(
|
||||
label: Text(AppLocalizations.of(context).editSchedule),
|
||||
onPressed: () {
|
||||
Navigator.pushNamed(
|
||||
context,
|
||||
FormScreen.routeName,
|
||||
arguments: FormScreenArguments(
|
||||
AppLocalizations.of(context).edit,
|
||||
MealForm(widget._meal.planId, widget._meal),
|
||||
),
|
||||
);
|
||||
},
|
||||
icon: const Icon(Icons.timer),
|
||||
),
|
||||
TextButton.icon(
|
||||
onPressed: () {
|
||||
// Delete the meal
|
||||
Provider.of<NutritionPlansProvider>(context, listen: false)
|
||||
.deleteMeal(widget._meal);
|
||||
|
||||
// and inform the user
|
||||
ScaffoldMessenger.of(context).showSnackBar(
|
||||
SnackBar(
|
||||
content: Text(
|
||||
AppLocalizations.of(context).successfullyDeleted,
|
||||
textAlign: TextAlign.center,
|
||||
),
|
||||
),
|
||||
);
|
||||
},
|
||||
label: Text(AppLocalizations.of(context).delete),
|
||||
icon: const Icon(Icons.delete)),
|
||||
],
|
||||
)),
|
||||
const Divider(),
|
||||
...widget._meal.mealItems
|
||||
.map((item) => MealItemWidget(item, _showingDetails, _editing)),
|
||||
],
|
||||
),
|
||||
),
|
||||
@@ -144,10 +138,11 @@ class _MealWidgetState extends State<MealWidget> {
|
||||
}
|
||||
|
||||
class MealItemWidget extends StatelessWidget {
|
||||
final bool _expanded;
|
||||
final bool _editing;
|
||||
final bool _showingDetails;
|
||||
final MealItem _item;
|
||||
|
||||
const MealItemWidget(this._item, this._expanded);
|
||||
const MealItemWidget(this._item, this._showingDetails, this._editing);
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
@@ -180,11 +175,12 @@ class MealItemWidget extends StatelessWidget {
|
||||
),
|
||||
subtitle: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [if (_expanded) ...getMutedNutritionalValues(values, context)],
|
||||
children: [if (_showingDetails) ...getMutedNutritionalValues(values, context)],
|
||||
),
|
||||
trailing: _expanded
|
||||
trailing: _editing
|
||||
? IconButton(
|
||||
icon: const Icon(Icons.delete),
|
||||
tooltip: AppLocalizations.of(context).delete,
|
||||
iconSize: ICON_SIZE_SMALL,
|
||||
onPressed: () {
|
||||
// Delete the meal item
|
||||
@@ -205,87 +201,95 @@ class MealItemWidget extends StatelessWidget {
|
||||
}
|
||||
}
|
||||
|
||||
class DismissibleMealHeader extends StatelessWidget {
|
||||
final bool _expanded;
|
||||
final Function _toggle;
|
||||
class MealHeader extends StatelessWidget {
|
||||
final bool _editing;
|
||||
final bool _showingDetails;
|
||||
final Function _toggleEditing;
|
||||
final Function _toggleDetails;
|
||||
|
||||
const DismissibleMealHeader(
|
||||
this._expanded,
|
||||
this._toggle, {
|
||||
const MealHeader({
|
||||
required Meal meal,
|
||||
}) : _meal = meal;
|
||||
required bool editing,
|
||||
required Function toggleEditing,
|
||||
required bool showingDetails,
|
||||
required Function toggleDetails,
|
||||
}) : _toggleDetails = toggleDetails,
|
||||
_toggleEditing = toggleEditing,
|
||||
_showingDetails = showingDetails,
|
||||
_editing = editing,
|
||||
_meal = meal;
|
||||
|
||||
final Meal _meal;
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Dismissible(
|
||||
key: Key(_meal.id.toString()),
|
||||
direction: DismissDirection.startToEnd,
|
||||
background: Container(
|
||||
color: Theme.of(context).primaryColor, //wgerPrimaryButtonColor,
|
||||
alignment: Alignment.centerLeft,
|
||||
padding: const EdgeInsets.only(left: 10),
|
||||
child: Column(
|
||||
mainAxisAlignment: MainAxisAlignment.center,
|
||||
children: [
|
||||
return Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
ListTile(
|
||||
contentPadding: const EdgeInsets.symmetric(horizontal: 16, vertical: 8),
|
||||
title: Row(children: [
|
||||
Expanded(
|
||||
child: (_meal.name != '')
|
||||
? Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Text(
|
||||
_meal.name,
|
||||
style: Theme.of(context).textTheme.titleMedium,
|
||||
),
|
||||
Text(
|
||||
_meal.time!.format(context),
|
||||
style: Theme.of(context).textTheme.headlineSmall,
|
||||
)
|
||||
],
|
||||
)
|
||||
: Text(
|
||||
_meal.time!.format(context),
|
||||
style: Theme.of(context).textTheme.headlineSmall,
|
||||
),
|
||||
),
|
||||
Text(
|
||||
AppLocalizations.of(context).logMeal,
|
||||
style: const TextStyle(color: Colors.white),
|
||||
AppLocalizations.of(context).log,
|
||||
style: Theme.of(context)
|
||||
.textTheme
|
||||
.labelLarge
|
||||
?.copyWith(color: Theme.of(context).colorScheme.primary),
|
||||
),
|
||||
const Icon(
|
||||
Icons.history_edu,
|
||||
color: Colors.white,
|
||||
const SizedBox(width: 26),
|
||||
const SizedBox(height: 40, width: 1, child: VerticalDivider()),
|
||||
]),
|
||||
trailing: Row(mainAxisSize: MainAxisSize.min, children: [
|
||||
IconButton(
|
||||
icon: _showingDetails ? const Icon(Icons.info) : const Icon(Icons.info_outline),
|
||||
onPressed: () {
|
||||
_toggleDetails();
|
||||
},
|
||||
tooltip: AppLocalizations.of(context).toggleDetails,
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
confirmDismiss: (direction) async {
|
||||
// Delete
|
||||
if (direction == DismissDirection.startToEnd) {
|
||||
Provider.of<NutritionPlansProvider>(context, listen: false).logMealToDiary(_meal);
|
||||
ScaffoldMessenger.of(context).showSnackBar(
|
||||
SnackBar(
|
||||
content: Text(
|
||||
AppLocalizations.of(context).mealLogged,
|
||||
textAlign: TextAlign.center,
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
return false;
|
||||
},
|
||||
child: Container(
|
||||
padding: const EdgeInsets.all(10),
|
||||
decoration: BoxDecoration(color: Theme.of(context).colorScheme.inversePrimary),
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
if (_meal.name != '')
|
||||
Text(
|
||||
_meal.name,
|
||||
style: Theme.of(context).textTheme.headlineSmall,
|
||||
),
|
||||
Row(
|
||||
children: [
|
||||
Expanded(
|
||||
child: Text(
|
||||
_meal.time!.format(context),
|
||||
style: Theme.of(context).textTheme.headlineSmall,
|
||||
),
|
||||
const SizedBox(width: 5),
|
||||
IconButton(
|
||||
icon: _editing ? const Icon(Icons.done) : const Icon(Icons.edit),
|
||||
tooltip:
|
||||
_editing ? AppLocalizations.of(context).done : AppLocalizations.of(context).edit,
|
||||
onPressed: () {
|
||||
_toggleEditing();
|
||||
},
|
||||
)
|
||||
]),
|
||||
onTap: () {
|
||||
Provider.of<NutritionPlansProvider>(context, listen: false).logMealToDiary(_meal);
|
||||
ScaffoldMessenger.of(context).showSnackBar(
|
||||
SnackBar(
|
||||
content: Text(
|
||||
AppLocalizations.of(context).mealLogged,
|
||||
textAlign: TextAlign.center,
|
||||
),
|
||||
IconButton(
|
||||
visualDensity: VisualDensity.compact,
|
||||
icon: _expanded ? const Icon(Icons.unfold_less) : const Icon(Icons.unfold_more),
|
||||
onPressed: () {
|
||||
_toggle();
|
||||
},
|
||||
),
|
||||
],
|
||||
),
|
||||
],
|
||||
),
|
||||
);
|
||||
},
|
||||
),
|
||||
),
|
||||
],
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -195,6 +195,7 @@ class NutritionalDiaryDetailWidget extends StatelessWidget {
|
||||
),
|
||||
),
|
||||
IconButton(
|
||||
tooltip: AppLocalizations.of(context).delete,
|
||||
onPressed: () {
|
||||
Provider.of<NutritionPlansProvider>(context, listen: false)
|
||||
.deleteLog(log.id!, _nutritionalPlan.id!);
|
||||
|
||||
@@ -39,78 +39,70 @@ class NutritionalPlansList extends StatelessWidget {
|
||||
itemCount: _nutritionProvider.items.length,
|
||||
itemBuilder: (context, index) {
|
||||
final currentPlan = _nutritionProvider.items[index];
|
||||
return Dismissible(
|
||||
key: Key(currentPlan.id.toString()),
|
||||
confirmDismiss: (direction) async {
|
||||
// Delete workout from DB
|
||||
final bool? res = await showDialog(
|
||||
context: context,
|
||||
builder: (BuildContext contextDialog) {
|
||||
return AlertDialog(
|
||||
content: Text(
|
||||
AppLocalizations.of(context).confirmDelete(currentPlan.description),
|
||||
),
|
||||
actions: [
|
||||
TextButton(
|
||||
child: Text(MaterialLocalizations.of(context).cancelButtonLabel),
|
||||
onPressed: () => Navigator.of(contextDialog).pop(),
|
||||
),
|
||||
TextButton(
|
||||
child: Text(
|
||||
AppLocalizations.of(context).delete,
|
||||
style: TextStyle(color: Theme.of(context).colorScheme.error),
|
||||
),
|
||||
onPressed: () {
|
||||
// Confirmed, delete the workout
|
||||
_nutritionProvider.deletePlan(currentPlan.id!);
|
||||
|
||||
// Close the popup
|
||||
Navigator.of(contextDialog).pop();
|
||||
|
||||
// and inform the user
|
||||
ScaffoldMessenger.of(context).showSnackBar(
|
||||
SnackBar(
|
||||
content: Text(
|
||||
AppLocalizations.of(context).successfullyDeleted,
|
||||
textAlign: TextAlign.center,
|
||||
),
|
||||
return Card(
|
||||
child: ListTile(
|
||||
onTap: () {
|
||||
Navigator.of(context).pushNamed(
|
||||
NutritionalPlanScreen.routeName,
|
||||
arguments: currentPlan,
|
||||
);
|
||||
},
|
||||
title: Text(currentPlan.getLabel(context)),
|
||||
subtitle: Text(
|
||||
DateFormat.yMd(Localizations.localeOf(context).languageCode)
|
||||
.format(currentPlan.creationDate),
|
||||
),
|
||||
trailing: Row(mainAxisSize: MainAxisSize.min, children: [
|
||||
const VerticalDivider(),
|
||||
IconButton(
|
||||
icon: const Icon(Icons.delete),
|
||||
tooltip: AppLocalizations.of(context).delete,
|
||||
onPressed: () async {
|
||||
// Delete workout from DB
|
||||
await showDialog(
|
||||
context: context,
|
||||
builder: (BuildContext contextDialog) {
|
||||
return AlertDialog(
|
||||
content: Text(
|
||||
AppLocalizations.of(context)
|
||||
.confirmDelete(currentPlan.description),
|
||||
),
|
||||
actions: [
|
||||
TextButton(
|
||||
child:
|
||||
Text(MaterialLocalizations.of(context).cancelButtonLabel),
|
||||
onPressed: () => Navigator.of(contextDialog).pop(),
|
||||
),
|
||||
);
|
||||
},
|
||||
),
|
||||
],
|
||||
);
|
||||
});
|
||||
return res;
|
||||
},
|
||||
background: Container(
|
||||
color: Theme.of(context).colorScheme.error,
|
||||
alignment: Alignment.centerRight,
|
||||
padding: const EdgeInsets.only(right: 20),
|
||||
margin: const EdgeInsets.symmetric(
|
||||
horizontal: 4,
|
||||
vertical: 4,
|
||||
),
|
||||
child: const Icon(
|
||||
Icons.delete,
|
||||
color: Colors.white,
|
||||
),
|
||||
),
|
||||
direction: DismissDirection.endToStart,
|
||||
child: Card(
|
||||
child: ListTile(
|
||||
onTap: () {
|
||||
Navigator.of(context).pushNamed(
|
||||
NutritionalPlanScreen.routeName,
|
||||
arguments: currentPlan,
|
||||
);
|
||||
},
|
||||
title: Text(currentPlan.getLabel(context)),
|
||||
subtitle: Text(
|
||||
DateFormat.yMd(Localizations.localeOf(context).languageCode)
|
||||
.format(currentPlan.creationDate),
|
||||
),
|
||||
),
|
||||
TextButton(
|
||||
child: Text(
|
||||
AppLocalizations.of(context).delete,
|
||||
style:
|
||||
TextStyle(color: Theme.of(context).colorScheme.error),
|
||||
),
|
||||
onPressed: () {
|
||||
// Confirmed, delete the workout
|
||||
_nutritionProvider.deletePlan(currentPlan.id!);
|
||||
|
||||
// Close the popup
|
||||
Navigator.of(contextDialog).pop();
|
||||
|
||||
// and inform the user
|
||||
ScaffoldMessenger.of(context).showSnackBar(
|
||||
SnackBar(
|
||||
content: Text(
|
||||
AppLocalizations.of(context).successfullyDeleted,
|
||||
textAlign: TextAlign.center,
|
||||
),
|
||||
),
|
||||
);
|
||||
},
|
||||
),
|
||||
],
|
||||
);
|
||||
});
|
||||
},
|
||||
)
|
||||
]),
|
||||
),
|
||||
);
|
||||
},
|
||||
|
||||
@@ -97,7 +97,7 @@ class WorkoutDayWidget extends StatefulWidget {
|
||||
}
|
||||
|
||||
class _WorkoutDayWidgetState extends State<WorkoutDayWidget> {
|
||||
bool _expanded = false;
|
||||
bool _editing = false;
|
||||
late List<Set> _sets;
|
||||
|
||||
@override
|
||||
@@ -109,20 +109,21 @@ class _WorkoutDayWidgetState extends State<WorkoutDayWidget> {
|
||||
|
||||
void _toggleExpanded() {
|
||||
setState(() {
|
||||
_expanded = !_expanded;
|
||||
_editing = !_editing;
|
||||
});
|
||||
}
|
||||
|
||||
Widget getSetRow(Set set, int index) {
|
||||
return Row(
|
||||
key: ValueKey(set.id),
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
crossAxisAlignment: CrossAxisAlignment.center,
|
||||
children: [
|
||||
if (_expanded)
|
||||
if (_editing)
|
||||
IconButton(
|
||||
visualDensity: VisualDensity.compact,
|
||||
icon: const Icon(Icons.delete),
|
||||
iconSize: ICON_SIZE_SMALL,
|
||||
tooltip: AppLocalizations.of(context).delete,
|
||||
onPressed: () {
|
||||
Provider.of<WorkoutPlansProvider>(context, listen: false).deleteSet(set);
|
||||
},
|
||||
@@ -135,7 +136,7 @@ class _WorkoutDayWidgetState extends State<WorkoutDayWidget> {
|
||||
(setting) => SettingWidget(
|
||||
set: set,
|
||||
setting: setting,
|
||||
expanded: _expanded,
|
||||
expanded: _editing,
|
||||
toggle: _toggleExpanded,
|
||||
),
|
||||
),
|
||||
@@ -143,7 +144,7 @@ class _WorkoutDayWidgetState extends State<WorkoutDayWidget> {
|
||||
],
|
||||
),
|
||||
),
|
||||
if (_expanded)
|
||||
if (_editing)
|
||||
ReorderableDragStartListener(
|
||||
index: index,
|
||||
child: const IconButton(
|
||||
@@ -162,62 +163,65 @@ class _WorkoutDayWidgetState extends State<WorkoutDayWidget> {
|
||||
child: Card(
|
||||
margin: EdgeInsets.zero,
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
DayHeaderDismissible(
|
||||
DayHeader(
|
||||
day: widget._day,
|
||||
expanded: _expanded,
|
||||
expanded: _editing,
|
||||
toggle: _toggleExpanded,
|
||||
),
|
||||
if (_expanded)
|
||||
Row(
|
||||
mainAxisSize: MainAxisSize.max,
|
||||
mainAxisAlignment: MainAxisAlignment.spaceAround,
|
||||
children: [
|
||||
IconButton(
|
||||
onPressed: () {
|
||||
Provider.of<WorkoutPlansProvider>(context, listen: false).deleteDay(
|
||||
widget._day,
|
||||
);
|
||||
},
|
||||
icon: const Icon(Icons.delete),
|
||||
),
|
||||
if (widget._day.sets.isNotEmpty)
|
||||
Ink(
|
||||
decoration: ShapeDecoration(
|
||||
color: Theme.of(context).primaryColor,
|
||||
shape: const CircleBorder(),
|
||||
),
|
||||
child: IconButton(
|
||||
icon: const Icon(Icons.play_arrow),
|
||||
color: Colors.white,
|
||||
if (_editing)
|
||||
Padding(
|
||||
padding: const EdgeInsets.symmetric(vertical: 8),
|
||||
child: Wrap(
|
||||
spacing: 8,
|
||||
children: [
|
||||
TextButton.icon(
|
||||
label: Text(AppLocalizations.of(context).addSet),
|
||||
icon: const Icon(Icons.add),
|
||||
onPressed: () {
|
||||
Navigator.of(context).pushNamed(
|
||||
GymModeScreen.routeName,
|
||||
arguments: widget._day,
|
||||
Navigator.pushNamed(
|
||||
context,
|
||||
FormScreen.routeName,
|
||||
arguments: FormScreenArguments(
|
||||
AppLocalizations.of(context).newSet,
|
||||
SetFormWidget(widget._day),
|
||||
hasListView: true,
|
||||
padding: EdgeInsets.zero,
|
||||
),
|
||||
);
|
||||
},
|
||||
),
|
||||
),
|
||||
IconButton(
|
||||
onPressed: () {
|
||||
Navigator.pushNamed(
|
||||
context,
|
||||
FormScreen.routeName,
|
||||
arguments: FormScreenArguments(
|
||||
AppLocalizations.of(context).edit,
|
||||
DayFormWidget(
|
||||
Provider.of<WorkoutPlansProvider>(context, listen: false)
|
||||
.findById(widget._day.workoutId),
|
||||
widget._day),
|
||||
hasListView: true,
|
||||
),
|
||||
);
|
||||
},
|
||||
icon: const Icon(Icons.edit),
|
||||
),
|
||||
],
|
||||
),
|
||||
if (_expanded) const Divider(),
|
||||
TextButton.icon(
|
||||
icon: const Icon(Icons.calendar_month),
|
||||
label: Text(AppLocalizations.of(context).editSchedule),
|
||||
onPressed: () {
|
||||
Navigator.pushNamed(
|
||||
context,
|
||||
FormScreen.routeName,
|
||||
arguments: FormScreenArguments(
|
||||
AppLocalizations.of(context).edit,
|
||||
DayFormWidget(
|
||||
Provider.of<WorkoutPlansProvider>(context, listen: false)
|
||||
.findById(widget._day.workoutId),
|
||||
widget._day),
|
||||
hasListView: true,
|
||||
),
|
||||
);
|
||||
},
|
||||
),
|
||||
TextButton.icon(
|
||||
icon: const Icon(Icons.delete),
|
||||
label: Text(AppLocalizations.of(context).delete),
|
||||
onPressed: () {
|
||||
Provider.of<WorkoutPlansProvider>(context, listen: false).deleteDay(
|
||||
widget._day,
|
||||
);
|
||||
},
|
||||
),
|
||||
],
|
||||
)),
|
||||
const Divider(),
|
||||
ReorderableListView(
|
||||
physics: const NeverScrollableScrollPhysics(),
|
||||
shrinkWrap: true,
|
||||
@@ -240,21 +244,6 @@ class _WorkoutDayWidgetState extends State<WorkoutDayWidget> {
|
||||
for (var i = 0; i < widget._day.sets.length; i++) getSetRow(widget._day.sets[i], i),
|
||||
],
|
||||
),
|
||||
OutlinedButton(
|
||||
child: Text(AppLocalizations.of(context).addSet),
|
||||
onPressed: () {
|
||||
Navigator.pushNamed(
|
||||
context,
|
||||
FormScreen.routeName,
|
||||
arguments: FormScreenArguments(
|
||||
AppLocalizations.of(context).newSet,
|
||||
SetFormWidget(widget._day),
|
||||
hasListView: true,
|
||||
padding: EdgeInsets.zero,
|
||||
),
|
||||
);
|
||||
},
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
@@ -262,77 +251,48 @@ class _WorkoutDayWidgetState extends State<WorkoutDayWidget> {
|
||||
}
|
||||
}
|
||||
|
||||
class DayHeaderDismissible extends StatelessWidget {
|
||||
class DayHeader extends StatelessWidget {
|
||||
final Day _day;
|
||||
final bool _expanded;
|
||||
final bool _editing;
|
||||
final Function _toggle;
|
||||
|
||||
const DayHeaderDismissible({
|
||||
const DayHeader({
|
||||
required Day day,
|
||||
required bool expanded,
|
||||
required Function toggle,
|
||||
}) : _day = day,
|
||||
_expanded = expanded,
|
||||
_editing = expanded,
|
||||
_toggle = toggle;
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Dismissible(
|
||||
key: Key(_day.id.toString()),
|
||||
direction: DismissDirection.startToEnd,
|
||||
background: Container(
|
||||
color: Theme.of(context).primaryColor,
|
||||
alignment: Alignment.centerLeft,
|
||||
padding: const EdgeInsets.only(left: 10),
|
||||
child: Column(
|
||||
mainAxisAlignment: MainAxisAlignment.center,
|
||||
children: [
|
||||
Text(
|
||||
AppLocalizations.of(context).gymMode,
|
||||
style: const TextStyle(color: Colors.white),
|
||||
),
|
||||
const Icon(
|
||||
Icons.play_arrow,
|
||||
color: Colors.white,
|
||||
),
|
||||
],
|
||||
),
|
||||
return ListTile(
|
||||
contentPadding: const EdgeInsets.symmetric(horizontal: 16, vertical: 8),
|
||||
title: Text(
|
||||
_day.description,
|
||||
style: Theme.of(context).textTheme.headlineSmall,
|
||||
overflow: TextOverflow.ellipsis,
|
||||
),
|
||||
confirmDismiss: (direction) async {
|
||||
// Delete day
|
||||
if (direction == DismissDirection.startToEnd) {
|
||||
Navigator.of(context).pushNamed(GymModeScreen.routeName, arguments: _day);
|
||||
}
|
||||
return false;
|
||||
subtitle: Text(_day.getDaysTextTranslated(Localizations.localeOf(context).languageCode)),
|
||||
leading: const Icon(Icons.play_arrow),
|
||||
minLeadingWidth: 8,
|
||||
trailing: Row(mainAxisSize: MainAxisSize.min, children: [
|
||||
const SizedBox(height: 40, width: 1, child: VerticalDivider()),
|
||||
const SizedBox(width: 10),
|
||||
IconButton(
|
||||
icon: _editing ? const Icon(Icons.done) : const Icon(Icons.edit),
|
||||
tooltip: _editing ? AppLocalizations.of(context).done : AppLocalizations.of(context).edit,
|
||||
onPressed: () {
|
||||
_toggle();
|
||||
},
|
||||
)
|
||||
]),
|
||||
onTap: () {
|
||||
Navigator.of(context).pushNamed(
|
||||
GymModeScreen.routeName,
|
||||
arguments: _day,
|
||||
);
|
||||
},
|
||||
child: Container(
|
||||
padding: const EdgeInsets.all(10),
|
||||
decoration: BoxDecoration(color: Theme.of(context).colorScheme.inversePrimary),
|
||||
child: Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
children: [
|
||||
Expanded(
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Text(
|
||||
_day.description,
|
||||
style: Theme.of(context).textTheme.headlineSmall,
|
||||
overflow: TextOverflow.ellipsis,
|
||||
),
|
||||
Text(_day.getDaysTextTranslated(Localizations.localeOf(context).languageCode)),
|
||||
],
|
||||
),
|
||||
),
|
||||
IconButton(
|
||||
icon: _expanded ? const Icon(Icons.unfold_less) : const Icon(Icons.unfold_more),
|
||||
onPressed: () {
|
||||
_toggle();
|
||||
},
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1131,7 +1131,7 @@ class NavigationHeader extends StatelessWidget {
|
||||
),
|
||||
),
|
||||
IconButton(
|
||||
icon: const Icon(Icons.menu),
|
||||
icon: const Icon(Icons.toc),
|
||||
onPressed: () {
|
||||
showDialog(
|
||||
context: context,
|
||||
|
||||
@@ -40,81 +40,71 @@ class WorkoutPlansList extends StatelessWidget {
|
||||
itemCount: _workoutProvider.items.length,
|
||||
itemBuilder: (context, index) {
|
||||
final currentWorkout = _workoutProvider.items[index];
|
||||
return Dismissible(
|
||||
key: Key(currentWorkout.id.toString()),
|
||||
confirmDismiss: (direction) async {
|
||||
// Delete workout from DB
|
||||
final res = await showDialog(
|
||||
context: context,
|
||||
builder: (BuildContext contextDialog) {
|
||||
return AlertDialog(
|
||||
content: Text(
|
||||
AppLocalizations.of(context).confirmDelete(currentWorkout.name),
|
||||
),
|
||||
actions: [
|
||||
TextButton(
|
||||
child: Text(MaterialLocalizations.of(context).cancelButtonLabel),
|
||||
onPressed: () => Navigator.of(contextDialog).pop(),
|
||||
),
|
||||
TextButton(
|
||||
child: Text(
|
||||
AppLocalizations.of(context).delete,
|
||||
style: TextStyle(color: Theme.of(context).colorScheme.error),
|
||||
),
|
||||
onPressed: () {
|
||||
// Confirmed, delete the workout
|
||||
Provider.of<WorkoutPlansProvider>(context, listen: false)
|
||||
.deleteWorkout(currentWorkout.id!);
|
||||
|
||||
// Close the popup
|
||||
Navigator.of(contextDialog).pop();
|
||||
|
||||
// and inform the user
|
||||
ScaffoldMessenger.of(context).showSnackBar(
|
||||
SnackBar(
|
||||
content: Text(
|
||||
AppLocalizations.of(context).successfullyDeleted,
|
||||
textAlign: TextAlign.center,
|
||||
),
|
||||
),
|
||||
);
|
||||
},
|
||||
),
|
||||
],
|
||||
);
|
||||
});
|
||||
return res;
|
||||
},
|
||||
background: Container(
|
||||
color: Theme.of(context).colorScheme.error,
|
||||
alignment: Alignment.centerRight,
|
||||
padding: const EdgeInsets.only(right: 20),
|
||||
margin: const EdgeInsets.symmetric(
|
||||
horizontal: 4,
|
||||
vertical: 4,
|
||||
),
|
||||
child: const Icon(
|
||||
Icons.delete,
|
||||
color: Colors.white,
|
||||
),
|
||||
),
|
||||
direction: DismissDirection.endToStart,
|
||||
child: Card(
|
||||
return Card(
|
||||
child: ListTile(
|
||||
onTap: () {
|
||||
_workoutProvider.setCurrentPlan(currentWorkout.id!);
|
||||
onTap: () {
|
||||
_workoutProvider.setCurrentPlan(currentWorkout.id!);
|
||||
|
||||
Navigator.of(context)
|
||||
.pushNamed(WorkoutPlanScreen.routeName, arguments: currentWorkout);
|
||||
},
|
||||
title: Text(currentWorkout.name),
|
||||
subtitle: Text(
|
||||
DateFormat.yMd(Localizations.localeOf(context).languageCode)
|
||||
.format(currentWorkout.creationDate),
|
||||
),
|
||||
),
|
||||
Navigator.of(context)
|
||||
.pushNamed(WorkoutPlanScreen.routeName, arguments: currentWorkout);
|
||||
},
|
||||
title: Text(currentWorkout.name),
|
||||
subtitle: Text(
|
||||
DateFormat.yMd(Localizations.localeOf(context).languageCode)
|
||||
.format(currentWorkout.creationDate),
|
||||
),
|
||||
);
|
||||
trailing: Row(mainAxisSize: MainAxisSize.min, children: [
|
||||
const VerticalDivider(),
|
||||
IconButton(
|
||||
icon: const Icon(Icons.delete),
|
||||
tooltip: AppLocalizations.of(context).delete,
|
||||
onPressed: () async {
|
||||
// Delete workout from DB
|
||||
await showDialog(
|
||||
context: context,
|
||||
builder: (BuildContext contextDialog) {
|
||||
return AlertDialog(
|
||||
content: Text(
|
||||
AppLocalizations.of(context).confirmDelete(currentWorkout.name),
|
||||
),
|
||||
actions: [
|
||||
TextButton(
|
||||
child:
|
||||
Text(MaterialLocalizations.of(context).cancelButtonLabel),
|
||||
onPressed: () => Navigator.of(contextDialog).pop(),
|
||||
),
|
||||
TextButton(
|
||||
child: Text(
|
||||
AppLocalizations.of(context).delete,
|
||||
style: TextStyle(color: Theme.of(context).colorScheme.error),
|
||||
),
|
||||
onPressed: () {
|
||||
// Confirmed, delete the workout
|
||||
Provider.of<WorkoutPlansProvider>(context, listen: false)
|
||||
.deleteWorkout(currentWorkout.id!);
|
||||
|
||||
// Close the popup
|
||||
Navigator.of(contextDialog).pop();
|
||||
|
||||
// and inform the user
|
||||
ScaffoldMessenger.of(context).showSnackBar(
|
||||
SnackBar(
|
||||
content: Text(
|
||||
AppLocalizations.of(context).successfullyDeleted,
|
||||
textAlign: TextAlign.center,
|
||||
),
|
||||
),
|
||||
);
|
||||
},
|
||||
),
|
||||
],
|
||||
);
|
||||
});
|
||||
},
|
||||
)
|
||||
]),
|
||||
));
|
||||
},
|
||||
),
|
||||
);
|
||||
|
||||
@@ -13,6 +13,9 @@ PODS:
|
||||
- FlutterMacOS
|
||||
- url_launcher_macos (0.0.1):
|
||||
- FlutterMacOS
|
||||
- video_player_avfoundation (0.0.1):
|
||||
- Flutter
|
||||
- FlutterMacOS
|
||||
|
||||
DEPENDENCIES:
|
||||
- file_selector_macos (from `Flutter/ephemeral/.symlinks/plugins/file_selector_macos/macos`)
|
||||
@@ -22,6 +25,7 @@ DEPENDENCIES:
|
||||
- rive_common (from `Flutter/ephemeral/.symlinks/plugins/rive_common/macos`)
|
||||
- shared_preferences_foundation (from `Flutter/ephemeral/.symlinks/plugins/shared_preferences_foundation/darwin`)
|
||||
- url_launcher_macos (from `Flutter/ephemeral/.symlinks/plugins/url_launcher_macos/macos`)
|
||||
- video_player_avfoundation (from `Flutter/ephemeral/.symlinks/plugins/video_player_avfoundation/darwin`)
|
||||
|
||||
EXTERNAL SOURCES:
|
||||
file_selector_macos:
|
||||
@@ -38,15 +42,18 @@ EXTERNAL SOURCES:
|
||||
:path: Flutter/ephemeral/.symlinks/plugins/shared_preferences_foundation/darwin
|
||||
url_launcher_macos:
|
||||
:path: Flutter/ephemeral/.symlinks/plugins/url_launcher_macos/macos
|
||||
video_player_avfoundation:
|
||||
:path: Flutter/ephemeral/.symlinks/plugins/video_player_avfoundation/darwin
|
||||
|
||||
SPEC CHECKSUMS:
|
||||
file_selector_macos: 0f85c1108e2fd597b58246bc0b0c1cb483d7593b
|
||||
file_selector_macos: 468fb6b81fac7c0e88d71317f3eec34c3b008ff9
|
||||
flutter_zxing: ea030278aa2a051cd81a5b0053be9d0569d11c9a
|
||||
FlutterMacOS: 8f6f14fa908a6fb3fba0cd85dbd81ec4b251fb24
|
||||
package_info_plus: 02d7a575e80f194102bef286361c6c326e4c29ce
|
||||
rive_common: acedcab7802c0ece4b0d838b71d7deb637e1309a
|
||||
shared_preferences_foundation: 986fc17f3d3251412d18b0265f9c64113a8c2472
|
||||
url_launcher_macos: 5335912b679c073563f29d89d33d10d459f95451
|
||||
rive_common: 0f0aadf670f0c6a7872dfe3e6186f112a5319108
|
||||
shared_preferences_foundation: 5b919d13b803cadd15ed2dc053125c68730e5126
|
||||
url_launcher_macos: d2691c7dd33ed713bf3544850a623080ec693d95
|
||||
video_player_avfoundation: 8563f13d8fc8b2c29dc2d09e60b660e4e8128837
|
||||
|
||||
PODFILE CHECKSUM: 0d3963a09fc94f580682bd88480486da345dc3f0
|
||||
|
||||
|
||||
@@ -80,7 +80,7 @@ void main() {
|
||||
expect(find.text('75g Burger soup'), findsOneWidget);
|
||||
expect(find.text('300g Broccoli cake'), findsOneWidget);
|
||||
|
||||
expect(find.byType(Dismissible), findsNWidgets(2));
|
||||
expect(find.byType(Card), findsNWidgets(2));
|
||||
expect(find.byType(FlNutritionalDiaryChartWidget), findsNothing);
|
||||
});
|
||||
|
||||
|
||||
@@ -86,14 +86,15 @@ void main() {
|
||||
|
||||
//debugDumpApp();
|
||||
expect(find.text('Nutritional plans'), findsOneWidget);
|
||||
expect(find.byType(Dismissible), findsNWidgets(2));
|
||||
expect(find.byType(Card), findsNWidgets(2));
|
||||
expect(find.byType(ListTile), findsNWidgets(2));
|
||||
});
|
||||
|
||||
testWidgets('Test deleting an item by dragging the dismissible', (WidgetTester tester) async {
|
||||
testWidgets('Test deleting an item using the Delete button', (WidgetTester tester) async {
|
||||
await tester.pumpWidget(createHomeScreen());
|
||||
|
||||
await tester.drag(find.byKey(const Key('1')), const Offset(-500.0, 0.0));
|
||||
await tester.tap(find.byIcon(Icons.delete).first);
|
||||
|
||||
await tester.pumpAndSettle();
|
||||
|
||||
// Confirmation dialog
|
||||
|
||||
@@ -90,7 +90,7 @@ void main() {
|
||||
expect(find.text('Bench press'), findsOneWidget);
|
||||
expect(find.text('Side raises'), findsOneWidget);
|
||||
expect(find.byIcon(Icons.close), findsOneWidget);
|
||||
expect(find.byIcon(Icons.menu), findsOneWidget);
|
||||
expect(find.byIcon(Icons.toc), findsOneWidget);
|
||||
expect(find.byIcon(Icons.chevron_left), findsNothing);
|
||||
expect(find.byIcon(Icons.chevron_right), findsOneWidget);
|
||||
await tester.tap(find.byIcon(Icons.chevron_right));
|
||||
@@ -102,7 +102,7 @@ void main() {
|
||||
expect(find.text('Bench press'), findsOneWidget);
|
||||
expect(find.byType(ExerciseOverview), findsOneWidget);
|
||||
expect(find.byIcon(Icons.close), findsOneWidget);
|
||||
expect(find.byIcon(Icons.menu), findsOneWidget);
|
||||
expect(find.byIcon(Icons.toc), findsOneWidget);
|
||||
expect(find.byIcon(Icons.chevron_left), findsOneWidget);
|
||||
expect(find.byIcon(Icons.chevron_right), findsOneWidget);
|
||||
await tester.drag(find.byType(ExerciseOverview), const Offset(-500.0, 0.0));
|
||||
@@ -119,7 +119,7 @@ void main() {
|
||||
expect(find.text('12 × 10 kg (2 RiR)'), findsOneWidget);
|
||||
expect(find.text('Make sure to warm up'), findsOneWidget, reason: 'Set comment');
|
||||
expect(find.byIcon(Icons.close), findsOneWidget);
|
||||
expect(find.byIcon(Icons.menu), findsOneWidget);
|
||||
expect(find.byIcon(Icons.toc), findsOneWidget);
|
||||
expect(find.byIcon(Icons.chevron_left), findsOneWidget);
|
||||
expect(find.byIcon(Icons.chevron_right), findsOneWidget);
|
||||
|
||||
@@ -145,7 +145,7 @@ void main() {
|
||||
expect(find.text('Pause'), findsOneWidget);
|
||||
expect(find.byType(TimerWidget), findsOneWidget);
|
||||
expect(find.byIcon(Icons.close), findsOneWidget);
|
||||
expect(find.byIcon(Icons.menu), findsOneWidget);
|
||||
expect(find.byIcon(Icons.toc), findsOneWidget);
|
||||
expect(find.byIcon(Icons.chevron_left), findsOneWidget);
|
||||
expect(find.byIcon(Icons.chevron_right), findsOneWidget);
|
||||
await tester.tap(find.byIcon(Icons.chevron_right));
|
||||
|
||||
@@ -72,7 +72,7 @@ void main() {
|
||||
expect(find.text('3 day workout'), findsOneWidget);
|
||||
expect(find.text('chest, shoulders'), findsOneWidget);
|
||||
expect(find.text('legs'), findsOneWidget);
|
||||
expect(find.byType(Dismissible), findsNWidgets(2));
|
||||
expect(find.byType(Card), findsNWidgets(2));
|
||||
});
|
||||
|
||||
testWidgets('Tests the localization of times - EN', (WidgetTester tester) async {
|
||||
|
||||
@@ -83,14 +83,15 @@ void main() {
|
||||
|
||||
//debugDumpApp();
|
||||
expect(find.text('Workout plans'), findsOneWidget);
|
||||
expect(find.byType(Dismissible), findsNWidgets(2));
|
||||
expect(find.byType(Card), findsNWidgets(2));
|
||||
expect(find.byType(ListTile), findsNWidgets(2));
|
||||
});
|
||||
|
||||
testWidgets('Test deleting an item by dragging the dismissible', (WidgetTester tester) async {
|
||||
testWidgets('Test deleting an item using the Delete button', (WidgetTester tester) async {
|
||||
await tester.pumpWidget(createHomeScreen());
|
||||
|
||||
await tester.drag(find.byKey(const Key('1')), const Offset(-500.0, 0.0));
|
||||
await tester.tap(find.byIcon(Icons.delete).first);
|
||||
|
||||
await tester.pumpAndSettle();
|
||||
|
||||
// Confirmation dialog
|
||||
|
||||
Reference in New Issue
Block a user