Added share menu to FormulaScreen
This commit is contained in:
parent
1757d13b6e
commit
8a42d53c77
3 changed files with 90 additions and 47 deletions
|
|
@ -1,6 +1,8 @@
|
||||||
|
import 'package:d4rt_formulas/error_handler.dart';
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:flutter/services.dart'; // For Clipboard
|
import 'package:flutter/services.dart'; // For Clipboard
|
||||||
import 'package:d4rt_formulas/formula_models.dart';
|
import 'package:d4rt_formulas/formula_models.dart';
|
||||||
|
import 'package:get_it/get_it.dart';
|
||||||
import '../corpus.dart';
|
import '../corpus.dart';
|
||||||
import '../set_utils.dart';
|
import '../set_utils.dart';
|
||||||
import 'formula_screen.dart';
|
import 'formula_screen.dart';
|
||||||
|
|
@ -22,6 +24,53 @@ class FormulaList extends StatefulWidget {
|
||||||
|
|
||||||
@override
|
@override
|
||||||
State<FormulaList> createState() => _FormulaListState();
|
State<FormulaList> createState() => _FormulaListState();
|
||||||
|
|
||||||
|
static String _formulaAndDependenciesToExportStringLiteral(Formula formula) {
|
||||||
|
final corpus = GetIt.instance.get<Corpus>();
|
||||||
|
final dependencies = corpus.withDependencies(formula);
|
||||||
|
final dependenciesAsMap = dependencies.map((f) => f.toMap()).toList();
|
||||||
|
for( final f in dependenciesAsMap ){
|
||||||
|
f.remove("uuid");
|
||||||
|
}
|
||||||
|
return SetUtils.prettyPrint(dependenciesAsMap);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static void shareFormula(Formula formula) async {
|
||||||
|
try {
|
||||||
|
final exportString = _formulaAndDependenciesToExportStringLiteral(formula);
|
||||||
|
|
||||||
|
// Share the string
|
||||||
|
await share_plus.SharePlus.instance.share(
|
||||||
|
share_plus.ShareParams(
|
||||||
|
text: exportString,
|
||||||
|
subject: 'Sharing formula: ${formula.name}',
|
||||||
|
),
|
||||||
|
);
|
||||||
|
} catch (e, st) {
|
||||||
|
errorHandler.notify(e, st);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static void copyFormula(BuildContext context, Formula formula) async {
|
||||||
|
try {
|
||||||
|
final exportString = _formulaAndDependenciesToExportStringLiteral(formula);
|
||||||
|
|
||||||
|
// Copy to clipboard
|
||||||
|
await Clipboard.setData(ClipboardData(text: exportString));
|
||||||
|
|
||||||
|
// Show a snackbar to confirm
|
||||||
|
ScaffoldMessenger.of(context).showSnackBar(
|
||||||
|
SnackBar(
|
||||||
|
content: Text('Formula and dependencies copied to clipboard!'),
|
||||||
|
duration: Duration(seconds: 2),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
} catch (e, st) {
|
||||||
|
errorHandler.notify(e, st);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
class _FormulaListState extends State<FormulaList> {
|
class _FormulaListState extends State<FormulaList> {
|
||||||
|
|
@ -56,49 +105,6 @@ class _FormulaListState extends State<FormulaList> {
|
||||||
}).toList();
|
}).toList();
|
||||||
}
|
}
|
||||||
|
|
||||||
String _formulaAndDependenciesToExportStringLiteral(Formula formula) {
|
|
||||||
final dependencies = widget.corpus.withDependencies(formula);
|
|
||||||
final dependenciesAsMap = dependencies.map((f) => f.toMap()).toList();
|
|
||||||
for( final f in dependenciesAsMap ){
|
|
||||||
f.remove("uuid");
|
|
||||||
}
|
|
||||||
return SetUtils.prettyPrint(dependenciesAsMap);
|
|
||||||
}
|
|
||||||
|
|
||||||
void _shareFormula(Formula formula) async {
|
|
||||||
try {
|
|
||||||
final exportString = _formulaAndDependenciesToExportStringLiteral(formula);
|
|
||||||
|
|
||||||
// Share the string
|
|
||||||
await share_plus.SharePlus.instance.share(
|
|
||||||
share_plus.ShareParams(
|
|
||||||
text: exportString,
|
|
||||||
subject: 'Sharing formula: ${formula.name}',
|
|
||||||
),
|
|
||||||
);
|
|
||||||
} catch (e) {
|
|
||||||
_showErrorDialog('Error sharing formula: $e');
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void _copyFormula(Formula formula) async {
|
|
||||||
try {
|
|
||||||
final exportString = _formulaAndDependenciesToExportStringLiteral(formula);
|
|
||||||
|
|
||||||
// Copy to clipboard
|
|
||||||
await Clipboard.setData(ClipboardData(text: exportString));
|
|
||||||
|
|
||||||
// Show a snackbar to confirm
|
|
||||||
ScaffoldMessenger.of(context).showSnackBar(
|
|
||||||
SnackBar(
|
|
||||||
content: Text('Formula and dependencies copied to clipboard!'),
|
|
||||||
duration: Duration(seconds: 2),
|
|
||||||
),
|
|
||||||
);
|
|
||||||
} catch (e) {
|
|
||||||
_showErrorDialog('Error copying formula: $e');
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void _showErrorDialog(String message) {
|
void _showErrorDialog(String message) {
|
||||||
showDialog(
|
showDialog(
|
||||||
|
|
@ -155,9 +161,9 @@ class _FormulaListState extends State<FormulaList> {
|
||||||
tooltip: 'Share or copy to clipboard',
|
tooltip: 'Share or copy to clipboard',
|
||||||
onSelected: (value) {
|
onSelected: (value) {
|
||||||
if (value == 'share') {
|
if (value == 'share') {
|
||||||
_shareFormula(formula);
|
FormulaList.shareFormula(formula);
|
||||||
} else if (value == 'copy') {
|
} else if (value == 'copy') {
|
||||||
_copyFormula(formula);
|
FormulaList.copyFormula(context, formula);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
itemBuilder: (context) => [
|
itemBuilder: (context) => [
|
||||||
|
|
|
||||||
|
|
@ -9,6 +9,7 @@ import '../corpus.dart';
|
||||||
import '../error_handler.dart';
|
import '../error_handler.dart';
|
||||||
import '../value_formatter.dart';
|
import '../value_formatter.dart';
|
||||||
import 'd4rt_editing_controller.dart';
|
import 'd4rt_editing_controller.dart';
|
||||||
|
import 'formula_list.dart';
|
||||||
import 'unit_dropdown.dart';
|
import 'unit_dropdown.dart';
|
||||||
import 'formula_editor.dart';
|
import 'formula_editor.dart';
|
||||||
|
|
||||||
|
|
@ -157,6 +158,42 @@ class _FormulaScreenState extends State<FormulaScreen> {
|
||||||
appBar: AppBar(
|
appBar: AppBar(
|
||||||
title: Text(formula.name),
|
title: Text(formula.name),
|
||||||
actions: [
|
actions: [
|
||||||
|
PopupMenuButton(
|
||||||
|
icon: const Icon(Icons.share),
|
||||||
|
tooltip: 'Share or copy to clipboard',
|
||||||
|
onSelected: (value) {
|
||||||
|
if (value == 'share') {
|
||||||
|
FormulaList.shareFormula(formula.originalFormula);
|
||||||
|
} else if (value == 'copy') {
|
||||||
|
FormulaList.copyFormula(context, formula.originalFormula);
|
||||||
|
}
|
||||||
|
},
|
||||||
|
itemBuilder: (context) => [
|
||||||
|
PopupMenuItem(
|
||||||
|
value: 'share',
|
||||||
|
child: Row(
|
||||||
|
mainAxisSize: MainAxisSize.min,
|
||||||
|
children: [
|
||||||
|
const Icon(Icons.share, size: 20),
|
||||||
|
const SizedBox(width: 8),
|
||||||
|
Flexible(child: Text('Share', softWrap: false)),
|
||||||
|
],
|
||||||
|
),
|
||||||
|
),
|
||||||
|
PopupMenuItem(
|
||||||
|
value: 'copy',
|
||||||
|
child: Row(
|
||||||
|
mainAxisSize: MainAxisSize.min,
|
||||||
|
children: [
|
||||||
|
const Icon(Icons.copy, size: 20),
|
||||||
|
const SizedBox(width: 8),
|
||||||
|
Flexible(child: Text('Copy to clipboard', softWrap: false)),
|
||||||
|
],
|
||||||
|
),
|
||||||
|
),
|
||||||
|
],
|
||||||
|
),
|
||||||
|
|
||||||
IconButton(
|
IconButton(
|
||||||
icon: const Icon(Icons.edit),
|
icon: const Icon(Icons.edit),
|
||||||
onPressed: formula is DerivedFormula
|
onPressed: formula is DerivedFormula
|
||||||
|
|
|
||||||
|
|
@ -423,7 +423,7 @@ Number functionSolver(
|
||||||
final Number dy = numericalDerivative(x);
|
final Number dy = numericalDerivative(x);
|
||||||
|
|
||||||
if (dy == 0 || dy.abs() < 1e-12) {
|
if (dy == 0 || dy.abs() < 1e-12) {
|
||||||
throw NoSolutionException("Derivative is zero or too small, cannot continue Newton-Raphson.");
|
throw NoSolutionException("Derivative is zero or too small, cannot continue Newton-Raphson: $dy");
|
||||||
}
|
}
|
||||||
|
|
||||||
final Number delta = y / dy;
|
final Number delta = y / dy;
|
||||||
|
|
@ -436,7 +436,7 @@ Number functionSolver(
|
||||||
// If step exploded, cap the step to a reasonable multiple of `step`
|
// If step exploded, cap the step to a reasonable multiple of `step`
|
||||||
final Number maxStepAllowed = step * 1e6;
|
final Number maxStepAllowed = step * 1e6;
|
||||||
if ((xNew - x).abs() > maxStepAllowed) {
|
if ((xNew - x).abs() > maxStepAllowed) {
|
||||||
xNew = x + (delta.isNegative ? -maxStepAllowed : maxStepAllowed);
|
xNew = x - (delta.isNegative ? -maxStepAllowed : maxStepAllowed);
|
||||||
}
|
}
|
||||||
|
|
||||||
x = xNew;
|
x = xNew;
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue