From 024c2397489e3e4ff3e9dd3f9f513b5247408e9b Mon Sep 17 00:00:00 2001 From: Ed Rivas Date: Wed, 12 Jul 2023 21:47:24 +0000 Subject: [PATCH] Improve simplification implementation --- lib/src/node/compile.dart | 50 ++++++++++++++++++--------------------- 1 file changed, 23 insertions(+), 27 deletions(-) diff --git a/lib/src/node/compile.dart b/lib/src/node/compile.dart index dd94b8455..38f727859 100644 --- a/lib/src/node/compile.dart +++ b/lib/src/node/compile.dart @@ -227,29 +227,25 @@ Importer _parseImporter(Object? importer) { /// Implements the simplification algorithm for custom function return values. /// {@link https://github.com/sass/sass/blob/main/spec/types/calculation.md#simplifying-a-calculationvalue} -dynamic simplify(dynamic value) { - if (value is SassCalculation) { - var simplifiedArgs = value.arguments.map(simplify).toList().cast(); - if (value.name == 'calc') { - return simplifiedArgs[0]; - } - if (value.name == 'clamp') { - return simplify(Function.apply(SassCalculation.clamp, simplifiedArgs)); - } - if (value.name == 'min') { - return simplify(Function.apply(SassCalculation.min, [simplifiedArgs])); - } - if (value.name == 'max') { - return simplify(Function.apply(SassCalculation.max, [simplifiedArgs])); - } - return SassCalculation.unsimplified(value.name, simplifiedArgs); - } - if (value is CalculationOperation) { - return simplify(SassCalculation.operate(value.operator, - simplify(value.left) as Object, simplify(value.right) as Object)); - } - return value; -} +Object simplify(Object value) => switch (value) { + SassCalculation() => switch (( + // Match against... + value.name, // ...the calculation name + value.arguments.map(simplify).toList() // ...and simplified arguments + )) { + ('calc', [var first, ...]) => first, + ('clamp', [var min, var value, var max]) => + SassCalculation.clamp(min, value, max), + ('clamp', _) => + throw ArgumentError('clamp() requires exactly 3 arguments.'), + ('min', var args) => SassCalculation.min(args), + ('max', var args) => SassCalculation.max(args), + (var name, var args) => SassCalculation.unsimplified(name, args) + }, + CalculationOperation() => simplify(SassCalculation.operate( + value.operator, simplify(value.left), simplify(value.right))), + _ => value, + }; /// Parses `functions` from [record] into a list of [Callable]s or /// [AsyncCallable]s. @@ -264,8 +260,8 @@ List _parseFunctions(Object? functions, {bool asynch = false}) { if (!asynch) { late Callable callable; callable = Callable.fromSignature(signature, (arguments) { - var result = (callback as Function)(toJSArray(arguments)); - result = simplify(result); + var result = + simplify((callback as Function)(toJSArray(arguments)) as Object); if (result is Value) return result; if (isPromise(result)) { throw 'Invalid return value for custom function ' @@ -286,8 +282,8 @@ List _parseFunctions(Object? functions, {bool asynch = false}) { result = await promiseToFuture(result as Promise); } - result = simplify(result); - if (result is Value) return result; + var simplified = simplify(result as Object); + if (simplified is Value) return simplified; throw 'Invalid return value for custom function ' '"${callable.name}": $result is not a sass.Value.'; });