|
| 1 | +// Copyright 2020-2024 Trust Computing GmbH. |
| 2 | +// This file is part of Litentry. |
| 3 | +// |
| 4 | +// Litentry is free software: you can redistribute it and/or modify |
| 5 | +// it under the terms of the GNU General Public License as published by |
| 6 | +// the Free Software Foundation, either version 3 of the License, or |
| 7 | +// (at your option) any later version. |
| 8 | +// |
| 9 | +// Litentry is distributed in the hope that it will be useful, |
| 10 | +// but WITHOUT ANY WARRANTY; without even the implied warranty of |
| 11 | +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| 12 | +// GNU General Public License for more details. |
| 13 | +// |
| 14 | +// You should have received a copy of the GNU General Public License |
| 15 | +// along with Litentry. If not, see <https://www.gnu.org/licenses/>. |
| 16 | + |
| 17 | +// SPDX-License-Identifier: GPL-3.0-or-later |
| 18 | + |
| 19 | +pragma solidity ^0.8.0; |
| 20 | +import "../openzeppelin/Strings.sol"; |
| 21 | +import "../openzeppelin/math/Math.sol"; |
| 22 | +library StringShift { |
| 23 | + /** |
| 24 | + * @dev Converts a uint256 input to a string and shifts the decimal point to the left by the specified number of places. |
| 25 | + * @param value The uint256 parameter to be processed. |
| 26 | + * @param decimal The number of decimal places to shift. |
| 27 | + * @return The processed string. |
| 28 | + */ |
| 29 | + function toShiftedString( |
| 30 | + uint256 value, |
| 31 | + uint256 decimal |
| 32 | + ) internal pure returns (string memory) { |
| 33 | + // Convert uint256 to string |
| 34 | + |
| 35 | + if (value == 0) { |
| 36 | + return "0"; |
| 37 | + } else { |
| 38 | + string memory str = Strings.toString(value); |
| 39 | + |
| 40 | + // Calculate the position to insert the decimal point |
| 41 | + uint256 len = bytes(str).length; |
| 42 | + uint256 digit = Math.log10(decimal); |
| 43 | + |
| 44 | + if (len <= digit) { |
| 45 | + // If the length is less than or equal to the number of digits, pad with leading zeros and add '0.' |
| 46 | + string memory leadingZeros = new string(digit - len); |
| 47 | + for (uint256 i = 0; i < digit - len; i++) { |
| 48 | + leadingZeros = string(abi.encodePacked("0", leadingZeros)); |
| 49 | + } |
| 50 | + str = string(abi.encodePacked("0.", leadingZeros, str)); |
| 51 | + } else { |
| 52 | + // Otherwise, insert the decimal point at the correct position |
| 53 | + str = string( |
| 54 | + abi.encodePacked( |
| 55 | + substring(str, 0, len - digit), |
| 56 | + ".", |
| 57 | + substring(str, len - digit, len) |
| 58 | + ) |
| 59 | + ); |
| 60 | + } |
| 61 | + |
| 62 | + // Remove trailing zeros after the decimal point |
| 63 | + str = removeTrailingZeros(str); |
| 64 | + |
| 65 | + return str; |
| 66 | + } |
| 67 | + } |
| 68 | + |
| 69 | + /** |
| 70 | + * @dev Extracts a substring from a given string. |
| 71 | + * @param str The original string. |
| 72 | + * @param start The starting position of the original string. |
| 73 | + * @param end The ending position of the original string. |
| 74 | + * @return The extracted substring. |
| 75 | + */ |
| 76 | + function substring( |
| 77 | + string memory str, |
| 78 | + uint256 start, |
| 79 | + uint256 end |
| 80 | + ) internal pure returns (string memory) { |
| 81 | + bytes memory strBytes = bytes(str); |
| 82 | + bytes memory result = new bytes(end - start); |
| 83 | + for (uint256 i = start; i < end; i++) { |
| 84 | + result[i - start] = strBytes[i]; |
| 85 | + } |
| 86 | + return string(result); |
| 87 | + } |
| 88 | + |
| 89 | + /** |
| 90 | + * @dev Removes trailing zeros after the decimal point in a string. |
| 91 | + * @param str The input string. |
| 92 | + * @return The processed string with trailing zeros removed. |
| 93 | + */ |
| 94 | + function removeTrailingZeros( |
| 95 | + string memory str |
| 96 | + ) internal pure returns (string memory) { |
| 97 | + bytes memory strBytes = bytes(str); |
| 98 | + uint256 len = strBytes.length; |
| 99 | + |
| 100 | + // Traverse from the end to find the position of the first non-zero character |
| 101 | + uint256 newLen = len; |
| 102 | + while (newLen > 0 && strBytes[newLen - 1] == "0") { |
| 103 | + newLen--; |
| 104 | + } |
| 105 | + |
| 106 | + // If the last character is a decimal point, remove it as well |
| 107 | + if (newLen > 0 && strBytes[newLen - 1] == ".") { |
| 108 | + newLen--; |
| 109 | + } |
| 110 | + |
| 111 | + // Create a new byte array and copy the content |
| 112 | + bytes memory trimmedBytes = new bytes(newLen); |
| 113 | + for (uint256 i = 0; i < newLen; i++) { |
| 114 | + trimmedBytes[i] = strBytes[i]; |
| 115 | + } |
| 116 | + |
| 117 | + return string(trimmedBytes); |
| 118 | + } |
| 119 | +} |
0 commit comments