InputNumber.js 6.95 KB
import template from "./InputNumber.html";
angular.module("esNgAntd").directive("esInputNumber", function () {
    return {
        controllerAs: "esInputNumber",
        restrict: "E",
        transclude: true,
        replace: true,
        scope: {
            defaultValue: "@",
            min: "@",
            max: "@",
            onChange: "&",
            value: "@",
            precision: "@",
            key: "@",
            step: "@",
            formatter: "&",
            parser: "&",
            disabled: "@",
        },
        controller: function ($scope, $element) {
            this.getContext = function () {
                return $scope;
            };

            $scope.state = {
                value: $scope.value || $scope.defaultValue,
                min: Number($scope.min),
                max: Number($scope.max),
                precision: Number($scope.precision) || 0,
                key: Number($scope.key),
                step: $scope.step || 1,
            };
            $scope.watch = {
                value: function (newVal) {
                    $scope.setValue(newVal);
                },
                disabled: function (newVal) {
                    if (
                        newVal === undefined ||
                        newVal === "false" ||
                        newVal === "0"
                    ) {
                        $scope.state.disabled = false;
                    } else if (
                        newVal === "true" ||
                        newVal === "1" ||
                        newVal === "disabled"
                    ) {
                        $scope.state.disabled = true;
                    }
                },
            };

            for (const key in $scope.watch) {
                $scope.$watch(key, $scope.watch[key], true);
            }

            $scope.multiply = function (num1, num2) {
                let baseNum = 0;

                try {
                    baseNum += num1.toString().split(".")[1].length;
                } catch (e) {}

                try {
                    baseNum += num2.toString().split(".")[1].length;
                } catch (e) {}

                return (
                    (Number(num1.toString().replace(".", "")) *
                        Number(num2.toString().replace(".", ""))) /
                    Math.pow(10, baseNum)
                );
            };

            $scope.toFixed = function (value, number = 2) {
                return parseFloat(
                    Math.floor($scope.multiply(value, Math.pow(10, number))) /
                        Math.pow(10, number)
                ).toFixed(number);
            };

            $scope.setValue = function (value) {
                if (
                    $scope.parser({
                        value: value,
                    }) !== undefined
                ) {
                    value = $scope.parser({
                        value: value,
                    });
                }

                if (
                    $scope.state.max !== null &&
                    $scope.state.max !== undefined &&
                    value !== "" &&
                    value > $scope.state.max
                ) {
                    value = $scope.state.max;
                }

                if (
                    $scope.state.min !== null &&
                    $scope.state.min !== undefined &&
                    value !== "" &&
                    value < $scope.state.min
                ) {
                    value = $scope.state.min;
                }

                if (!/\d+/.test(value)) {
                    $scope.state.value = "";
                    value = "";
                }

                if ($scope.state.precision === 0 && value !== "") {
                    value = parseInt(value);
                }

                if ($scope.state.precision > 0 && value !== "") {
                    value = $scope.toFixed(value, $scope.state.precision);
                }

                if (
                    $scope.formatter({
                        value: value,
                    }) !== undefined
                ) {
                    value = $scope.formatter({
                        value: value,
                    });
                }

                $scope.state.value = value;

                if (
                    $scope.parser({
                        value: value || "",
                    }) !== undefined
                ) {
                    value = $scope.parser({
                        value: value || "",
                    });
                }

                $scope.onChange({
                    value: value,
                });
            };

            $scope.sum = function (num1, num2) {
                return (
                    ($scope.pow(num1) + $scope.pow(num2)) /
                    $scope.pow(1)
                ).toFixed($scope.precision);
            };

            $scope.reduce = function (num1, num2) {
                return (
                    ($scope.pow(num1) - $scope.pow(num2)) /
                    $scope.pow(1)
                ).toFixed($scope.precision);
            };

            $scope.pow = function (number, baseNum) {
                let str = String(number);

                if (str.indexOf(".") !== -1) {
                    return parseInt(str.replace(".", ""));
                } else {
                    return (
                        number * Math.pow(10, baseNum || $scope.precision || 0)
                    );
                }
            };

            $scope.handleClick = function (type) {
                let value = null;

                if (!$scope.state.value) {
                    value = 0;
                } else {
                    value = $scope.state.value;
                }

                if (
                    $scope.parser({
                        value: value || "",
                    })
                ) {
                    value = $scope.parser({
                        value: value || "",
                    });
                }

                if (type === "up") {
                    $scope.setValue($scope.sum(value, $scope.state.step));
                } else {
                    $scope.setValue($scope.reduce(value, $scope.state.step));
                }
            };

            $scope.handleClickInput = function (event) {
                $scope.state.inputEvent = event;
            };

            $scope.handleBlur = function (event) {
                $scope.setValue(event.target.value);
            };
        },
        link: function ($scope, $element, $attrs, $controllers, $transclude) {
            $scope.inputElement = $element[0].querySelector("input");
            $element[0].removeAttribute("ng-class");
            $element[0].removeAttribute("value");
            $element[0].removeAttribute("formatter");
            $element[0].removeAttribute("parser");
            $element[0].removeAttribute("on-change");
            $element[0].removeAttribute("disabled");
        },
    };
});