persian-number-input 3.0.10 → 4.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +144 -72
- package/dist/components/PersianNumberInput.d.ts +7 -8
- package/dist/components/PersianNumberInput.d.ts.map +1 -0
- package/dist/components/PersianNumberInput.js +33 -30
- package/dist/components/PersianNumberInput.js.map +1 -1
- package/dist/hooks/usePersianNumberInput.d.ts +21 -0
- package/dist/hooks/usePersianNumberInput.d.ts.map +1 -0
- package/dist/hooks/usePersianNumberInput.js +139 -0
- package/dist/hooks/usePersianNumberInput.js.map +1 -0
- package/dist/index.d.ts +5 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +27 -1
- package/dist/index.js.map +1 -1
- package/dist/utils/digitUtils.d.ts +45 -3
- package/dist/utils/digitUtils.d.ts.map +1 -0
- package/dist/utils/digitUtils.js +103 -34
- package/dist/utils/digitUtils.js.map +1 -1
- package/dist/utils/transformNumber.d.ts +21 -0
- package/dist/utils/transformNumber.d.ts.map +1 -0
- package/dist/utils/transformNumber.js +77 -0
- package/dist/utils/transformNumber.js.map +1 -0
- package/package.json +2 -2
package/README.md
CHANGED
|
@@ -4,34 +4,36 @@
|
|
|
4
4
|
|
|
5
5
|
---
|
|
6
6
|
|
|
7
|
-
|
|
7
|
+
English 🇺🇸 | فارسی 🇮🇷
|
|
8
8
|
|
|
9
9
|
---
|
|
10
10
|
|
|
11
|
-
##
|
|
11
|
+
## English
|
|
12
12
|
|
|
13
|
-
Persian Number Input - React
|
|
14
|
-
|
|
15
|
-
Easily input, format, and convert numbers in Persian, English, or Indic digits with customizable digit separators. Lightweight, React-compatible, and fully localized for React versions 16 to 19.
|
|
13
|
+
**Persian Number Input** - A powerful React component for formatting and handling numbers in Persian, English, or other localized digit systems. Perfect for multilingual applications requiring numeric inputs with customizable formatting.
|
|
16
14
|
|
|
17
15
|
✅ **Key Features:**
|
|
18
16
|
|
|
19
|
-
-
|
|
20
|
-
- Customizable digit grouping
|
|
21
|
-
-
|
|
22
|
-
-
|
|
17
|
+
- Supports Persian, English, and other digit localization (e.g., Indic)
|
|
18
|
+
- Customizable digit grouping (e.g., thousands separator)
|
|
19
|
+
- Handles decimal numbers with configurable precision
|
|
20
|
+
- Min/max value constraints for input validation
|
|
21
|
+
- Converts localized digits to standard English digits for processing
|
|
22
|
+
- Lightweight and compatible with React 16 to 19
|
|
23
|
+
- TypeScript support for robust development
|
|
23
24
|
|
|
24
25
|
### 🚀 Installation
|
|
25
26
|
|
|
27
|
+
Install the package via npm or yarn:
|
|
28
|
+
|
|
26
29
|
```bash
|
|
27
30
|
npm install persian-number-input
|
|
28
31
|
```
|
|
29
32
|
|
|
30
|
-

|
|
31
33
|
|
|
32
34
|
### 💻 Usage Example
|
|
33
35
|
|
|
34
|
-
|
|
36
|
+
Here’s a simple example demonstrating the component with min/max constraints and decimal support:
|
|
35
37
|
|
|
36
38
|
```jsx
|
|
37
39
|
import React, { useState } from "react";
|
|
@@ -42,10 +44,17 @@ const App = () => {
|
|
|
42
44
|
|
|
43
45
|
return (
|
|
44
46
|
<PersianNumberInput
|
|
45
|
-
initialValue="123456"
|
|
47
|
+
initialValue="123456.78"
|
|
46
48
|
separatorCount={3}
|
|
47
|
-
|
|
48
|
-
|
|
49
|
+
separatorChar=","
|
|
50
|
+
locale="fa"
|
|
51
|
+
maxDecimals={2}
|
|
52
|
+
min={0}
|
|
53
|
+
max={1000000}
|
|
54
|
+
showZero={true}
|
|
55
|
+
onValueChange={(val) => setNumber(val || "")}
|
|
56
|
+
placeholder="Enter a number"
|
|
57
|
+
className="numeric-input"
|
|
49
58
|
/>
|
|
50
59
|
);
|
|
51
60
|
};
|
|
@@ -56,82 +65,102 @@ export default App;
|
|
|
56
65
|
### 🔥 Output Example
|
|
57
66
|
|
|
58
67
|
```
|
|
59
|
-
Input: 123456
|
|
60
|
-
Displayed Output:
|
|
61
|
-
English Output: 123456
|
|
68
|
+
Input: 123456.78
|
|
69
|
+
Displayed Output: ۱۲۳,۴۵۶٫۷۸
|
|
70
|
+
English Output: 123456.78
|
|
62
71
|
```
|
|
63
72
|
|
|
64
|
-

|
|
65
|
-
|
|
66
73
|
### 📚 Props Reference
|
|
67
74
|
|
|
68
|
-
| Name
|
|
69
|
-
|
|
|
70
|
-
| initialValue
|
|
71
|
-
| separatorCount | number
|
|
72
|
-
| separatorChar
|
|
73
|
-
|
|
|
74
|
-
|
|
|
75
|
-
|
|
76
|
-
|
|
75
|
+
| Name | Type | Default | Description |
|
|
76
|
+
| --- | --- | --- | --- |
|
|
77
|
+
| `initialValue` | \`string | number\` | `""` |
|
|
78
|
+
| `separatorCount` | `number` | `3` | Number of digits per group (e.g., 3 for thousands) |
|
|
79
|
+
| `separatorChar` | `string` | `","` | Character used for grouping digits (e.g., `,` or `.`) |
|
|
80
|
+
| `locale` | `string` | `"fa"` | Language for digit localization (e.g., `fa`, `en`) |
|
|
81
|
+
| `maxDecimals` | `number` | `0` | Maximum number of decimal places allowed |
|
|
82
|
+
| `showZero` | `boolean` | `false` | If `true`, displays `0` when the input is empty or zero |
|
|
83
|
+
| `min` | `number` | \- | Minimum allowed value (inclusive) |
|
|
84
|
+
| `max` | `number` | \- | Maximum allowed value (inclusive) |
|
|
85
|
+
| `onValueChange` | \`(value: string | undefined) => void\` | \- |
|
|
86
|
+
| `...rest` | `InputHTMLAttributes` | \- | Standard HTML input attributes (e.g., `className`, `placeholder`, `style`) |
|
|
87
|
+
|
|
88
|
+
### 🌟 Why Use Persian Number Input?
|
|
89
|
+
|
|
90
|
+
- **Multilingual Support**: Seamlessly handle Persian, English, or other localized digits.
|
|
91
|
+
- **Customizable Formatting**: Control separators, decimals, and zero display.
|
|
92
|
+
- **Robust Validation**: Enforce min/max constraints for reliable inputs.
|
|
93
|
+
- **Developer-Friendly**: TypeScript support and a simple API for quick integration.
|
|
94
|
+
- **Lightweight**: Minimal bundle size for fast performance.
|
|
77
95
|
|
|
78
96
|
### ❓ FAQ (Frequently Asked Questions)
|
|
79
97
|
|
|
80
|
-
**Does this package support React 19
|
|
81
|
-
Yes, it fully
|
|
98
|
+
**Does this package support React 19?**\
|
|
99
|
+
Yes, it is fully compatible with React 16 through 19.
|
|
82
100
|
|
|
83
|
-
**
|
|
84
|
-
|
|
101
|
+
**Can I use decimal numbers?**\
|
|
102
|
+
Yes, set `maxDecimals` to the desired number of decimal places (e.g., `maxDecimals={2}`).
|
|
85
103
|
|
|
86
|
-
**How
|
|
87
|
-
|
|
104
|
+
**How do I enforce minimum and maximum values?**\
|
|
105
|
+
Use the `min` and `max` props to restrict the input range (e.g., `min={0}` and `max={1000}`).
|
|
88
106
|
|
|
89
|
-
|
|
107
|
+
**How can I style the input?**\
|
|
108
|
+
Pass `className` or `style` props to customize the input’s appearance.
|
|
109
|
+
|
|
110
|
+
**What happens if the user enters an invalid number?**\
|
|
111
|
+
The component sanitizes inputs, ensuring only valid numbers are processed, and respects min/max constraints.
|
|
90
112
|
|
|
91
113
|
### 🌟 Support the Project
|
|
92
114
|
|
|
93
|
-
If you find this package
|
|
115
|
+
If you find this package useful, **please give it a star ⭐ on GitHub** to support further development.
|
|
94
116
|
|
|
95
|
-
👉 **
|
|
117
|
+
👉 **GitHub Repository**
|
|
96
118
|
|
|
97
119
|
Thank you for your support! ❤️🚀
|
|
98
120
|
|
|
99
|
-
---
|
|
100
|
-
|
|
101
121
|
### 📈 SEO Keywords
|
|
102
122
|
|
|
103
|
-
`Persian Number Input`, `React Persian input`, `
|
|
104
|
-
|
|
105
|
-
---
|
|
123
|
+
`Persian Number Input`, `React Persian input`, `React number formatting`, `localized numeric input`, `Persian digits`, `React numeric input`, `number formatter`, `TypeScript React component`, `multilingual input`
|
|
106
124
|
|
|
107
125
|
### 📄 License
|
|
108
126
|
|
|
109
|
-
|
|
127
|
+
MIT License
|
|
110
128
|
|
|
111
|
-
©
|
|
129
|
+
© 2025 Javad Sharifi. All rights reserved.
|
|
112
130
|
|
|
113
|
-
|
|
131
|
+
---
|
|
114
132
|
|
|
115
|
-
##
|
|
133
|
+
## فارسی
|
|
116
134
|
|
|
117
|
-
کامپوننت React برای
|
|
135
|
+
**کامپوننت ورودی اعداد فارسی** - یک کامپوننت قدرتمند React برای مدیریت و فرمتبندی اعداد به صورت فارسی، انگلیسی یا سایر سیستمهای ارقام محلی. ایدهآل برای برنامههای چندزبانه که نیاز به ورودیهای عددی با فرمت سفارشی دارند.
|
|
118
136
|
|
|
119
137
|
✅ **امکانات کلیدی:**
|
|
120
138
|
|
|
121
|
-
- پشتیبانی از
|
|
122
|
-
- قابلیت
|
|
123
|
-
-
|
|
124
|
-
-
|
|
139
|
+
- پشتیبانی از ارقام فارسی، انگلیسی و سایر زبانها (مانند هندی)
|
|
140
|
+
- قابلیت تنظیم جداکننده ارقام (مثل هزارگان)
|
|
141
|
+
- مدیریت اعداد اعشاری با دقت قابل تنظیم
|
|
142
|
+
- اعمال محدودیتهای حداقل و حداکثر برای اعتبارسنجی
|
|
143
|
+
- تبدیل خودکار ارقام محلی به ارقام انگلیسی برای پردازش
|
|
144
|
+
- سبک و سازگار با React 16 تا 19
|
|
145
|
+
- پشتیبانی از TypeScript برای توسعه امن
|
|
125
146
|
|
|
126
147
|
### 🚀 نصب
|
|
127
148
|
|
|
149
|
+
پکیج را از طریق npm یا yarn نصب کنید:
|
|
150
|
+
|
|
128
151
|
```bash
|
|
129
152
|
npm install persian-number-input
|
|
130
153
|
```
|
|
131
154
|
|
|
132
|
-
|
|
155
|
+
یا
|
|
133
156
|
|
|
134
|
-
|
|
157
|
+
```bash
|
|
158
|
+
yarn add persian-number-input
|
|
159
|
+
```
|
|
160
|
+
|
|
161
|
+
### 💻 مثال استفاده
|
|
162
|
+
|
|
163
|
+
مثالی ساده با پشتیبانی از اعشار و محدودیتهای حداقل/حداکثر:
|
|
135
164
|
|
|
136
165
|
```jsx
|
|
137
166
|
import React, { useState } from "react";
|
|
@@ -142,10 +171,17 @@ const App = () => {
|
|
|
142
171
|
|
|
143
172
|
return (
|
|
144
173
|
<PersianNumberInput
|
|
145
|
-
initialValue="123456"
|
|
174
|
+
initialValue="123456.78"
|
|
146
175
|
separatorCount={3}
|
|
147
|
-
|
|
148
|
-
|
|
176
|
+
separatorChar=","
|
|
177
|
+
locale="fa"
|
|
178
|
+
maxDecimals={2}
|
|
179
|
+
min={0}
|
|
180
|
+
max={1000000}
|
|
181
|
+
showZero={true}
|
|
182
|
+
onValueChange={(val) => setNumber(val || "")}
|
|
183
|
+
placeholder="یک عدد وارد کنید"
|
|
184
|
+
className="numeric-input"
|
|
149
185
|
/>
|
|
150
186
|
);
|
|
151
187
|
};
|
|
@@ -156,29 +192,65 @@ export default App;
|
|
|
156
192
|
### 🔥 مثال خروجی
|
|
157
193
|
|
|
158
194
|
```
|
|
159
|
-
ورودی: 123456
|
|
160
|
-
خروجی نمایشی:
|
|
161
|
-
خروجی انگلیسی: 123456
|
|
195
|
+
ورودی: 123456.78
|
|
196
|
+
خروجی نمایشی: ۱۲۳,۴۵۶٫۷۸
|
|
197
|
+
خروجی انگلیسی: 123456.78
|
|
162
198
|
```
|
|
163
199
|
|
|
164
|
-
|
|
200
|
+
### 📚 مرجع مشخصات (Props)
|
|
165
201
|
|
|
166
|
-
|
|
202
|
+
| نام | نوع | پیشفرض | توضیح |
|
|
203
|
+
| --- | --- | --- | --- |
|
|
204
|
+
| `initialValue` | \`string | number\` | `""` |
|
|
205
|
+
| `separatorCount` | `number` | `3` | تعداد ارقام در هر گروه (مثلاً ۳ برای هزارگان) |
|
|
206
|
+
| `separatorChar` | `string` | `","` | کاراکتر جداکننده گروهها (مثلاً `,` یا `.`) |
|
|
207
|
+
| `locale` | `string` | `"fa"` | زبان برای محلیسازی ارقام (مثلاً `fa` یا `en`) |
|
|
208
|
+
| `maxDecimals` | `number` | `0` | حداکثر تعداد ارقام اعشاری مجاز |
|
|
209
|
+
| `showZero` | `boolean` | `false` | اگر `true` باشد، عدد `0` را در ورودی خالی یا صفر نمایش میدهد |
|
|
210
|
+
| `min` | `number` | \- | حداقل مقدار مجاز (شامل) |
|
|
211
|
+
| `max` | `number` | \- | حداکثر مقدار مجاز (شامل) |
|
|
212
|
+
| `onValueChange` | \`(value: string | undefined) => void\` | \- |
|
|
213
|
+
| `...rest` | `InputHTMLAttributes` | \- | ویژگیهای استاندارد ورودی HTML (مثل `className`، `placeholder`، `style`) |
|
|
167
214
|
|
|
168
|
-
|
|
169
|
-
| -------------- | ------------------------------- | ------ | -------------------------------- |
|
|
170
|
-
| initialValue | string | "" | مقدار اولیه |
|
|
171
|
-
| separatorCount | number | 0 | تعداد ارقام جداشده (مثلاً ۳ رقم) |
|
|
172
|
-
| separatorChar | string | "," | کاراکتر جداکننده (مانند `,`) |
|
|
173
|
-
| lang | 'fa' \| 'in' \| 'en' | "fa" | زبان نمایش ارقام |
|
|
174
|
-
| onChangeValue | (englishNumber: string) => void | - | فراخوانی در تغییر مقدار |
|
|
215
|
+
### 🌟 چرا از این کامپوننت استفاده کنیم؟
|
|
175
216
|
|
|
176
|
-
|
|
217
|
+
- **پشتیبانی چندزبانه**: مدیریت آسان ارقام فارسی، انگلیسی یا سایر زبانها.
|
|
218
|
+
- **فرمتبندی انعطافپذیر**: کنترل جداکنندهها، اعشار و نمایش صفر.
|
|
219
|
+
- **اعتبارسنجی قوی**: اعمال محدودیتهای حداقل و حداکثر برای ورودیهای مطمئن.
|
|
220
|
+
- **مناسب توسعهدهندگان**: پشتیبانی از TypeScript و API ساده برای ادغام سریع.
|
|
221
|
+
- **سبک و سریع**: حجم کم برای عملکرد بهینه.
|
|
222
|
+
|
|
223
|
+
### ❓ سوالات متداول
|
|
224
|
+
|
|
225
|
+
**آیا این پکیج از React 19 پشتیبانی میکند؟**\
|
|
226
|
+
بله، کاملاً با React 16 تا 19 سازگار است.
|
|
227
|
+
|
|
228
|
+
**آیا میتوان از اعداد اعشاری استفاده کرد؟**\
|
|
229
|
+
بله، با تنظیم `maxDecimals` میتوانید تعداد ارقام اعشاری را مشخص کنید (مثلاً `maxDecimals={2}`).
|
|
230
|
+
|
|
231
|
+
**چگونه میتوان حداقل و حداکثر مقدار را اعمال کرد؟**\
|
|
232
|
+
از پراپهای `min` و `max` استفاده کنید (مثلاً `min={0}` و `max={1000}`).
|
|
233
|
+
|
|
234
|
+
**چگونه ظاهر ورودی را سفارشی کنم؟**\
|
|
235
|
+
با پراپهای `className` یا `style` میتوانید ظاهر ورودی را تغییر دهید.
|
|
236
|
+
|
|
237
|
+
**اگر کاربر عدد نامعتبری وارد کند چه میشود؟**\
|
|
238
|
+
کامپوننت ورودیها را پاکسازی میکند و فقط اعداد معتبر را پردازش میکند، ضمن رعایت محدودیتهای min/max.
|
|
177
239
|
|
|
178
240
|
### 🌟 حمایت از پروژه
|
|
179
241
|
|
|
180
|
-
اگر این پکیج برای شما مفید بود، **لطفاً یک ستاره به مخزن GitHub
|
|
242
|
+
اگر این پکیج برای شما مفید بود، **لطفاً یک ستاره ⭐ به مخزن GitHub بدهید** تا توسعه بیشتر آن را تشویق کنید.
|
|
243
|
+
|
|
244
|
+
👉 **مخزن GitHub**
|
|
245
|
+
|
|
246
|
+
از حمایت شما سپاسگزاریم! ❤️🚀
|
|
247
|
+
|
|
248
|
+
### 📈 کلمات کلیدی برای جستجو
|
|
249
|
+
|
|
250
|
+
`ورودی اعداد فارسی`, `کامپوننت React فارسی`, `فرمتبندی اعداد در React`, `ورودی عددی محلیسازیشده`, `ارقام فارسی`, `ورودی عددی React`, `فرمتکننده اعداد`, `کامپوننت TypeScript React`, `ورودی چندزبانه`
|
|
251
|
+
|
|
252
|
+
### 📄 مجوز
|
|
181
253
|
|
|
182
|
-
|
|
254
|
+
MIT License
|
|
183
255
|
|
|
184
|
-
|
|
256
|
+
© ۱۴۰۴ جواد شریفی. تمامی حقوق محفوظ است.
|
|
@@ -1,12 +1,11 @@
|
|
|
1
1
|
import React from 'react';
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
2
|
+
import type { TransformNumberOptions } from '../utils/transformNumber';
|
|
3
|
+
interface PersianNumberInputProps extends TransformNumberOptions, Omit<React.InputHTMLAttributes<HTMLInputElement>, 'onChange' | 'value'> {
|
|
4
|
+
onValueChange?: (value: string | undefined) => void;
|
|
5
|
+
initialValue?: number | string;
|
|
6
|
+
min?: number;
|
|
7
|
+
max?: number;
|
|
8
8
|
}
|
|
9
|
-
type AllowedInputProps = Pick<React.InputHTMLAttributes<HTMLInputElement>, 'className' | 'style' | 'placeholder' | 'disabled' | 'readOnly' | 'id' | 'name' | 'autoComplete' | 'autoFocus' | 'maxLength' | 'minLength' | 'required' | 'title' | 'dir' | 'onClick' | 'onKeyDown' | 'onKeyUp' | 'onKeyPress' | 'onFocus' | 'onBlur' | 'onMouseDown' | 'onMouseUp' | 'onMouseEnter' | 'onMouseLeave' | 'onTouchStart' | 'onTouchEnd' | 'onPaste'>;
|
|
10
|
-
export type PersianNumberInputProps = PersianNumberInputCustomProps & AllowedInputProps;
|
|
11
9
|
declare const PersianNumberInput: React.FC<PersianNumberInputProps>;
|
|
12
10
|
export default PersianNumberInput;
|
|
11
|
+
//# sourceMappingURL=PersianNumberInput.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"PersianNumberInput.d.ts","sourceRoot":"","sources":["../../src/components/PersianNumberInput.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,MAAM,OAAO,CAAC;AAE1B,OAAO,KAAK,EAAE,sBAAsB,EAAE,MAAM,0BAA0B,CAAC;AAGvE,UAAU,uBACN,SAAQ,sBAAsB,EAC9B,IAAI,CAAC,KAAK,CAAC,mBAAmB,CAAC,gBAAgB,CAAC,EAAE,UAAU,GAAG,OAAO,CAAC;IAEvE,aAAa,CAAC,EAAE,CAAC,KAAK,EAAE,MAAM,GAAG,SAAS,KAAK,IAAI,CAAC;IACpD,YAAY,CAAC,EAAE,MAAM,GAAG,MAAM,CAAC;IAC/B,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,GAAG,CAAC,EAAE,MAAM,CAAC;CAChB;AAED,QAAA,MAAM,kBAAkB,EAAE,KAAK,CAAC,EAAE,CAAC,uBAAuB,CAiDzD,CAAC;AAEF,eAAe,kBAAkB,CAAC"}
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
"use strict";
|
|
1
2
|
var __rest = (this && this.__rest) || function (s, e) {
|
|
2
3
|
var t = {};
|
|
3
4
|
for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0)
|
|
@@ -9,36 +10,38 @@ var __rest = (this && this.__rest) || function (s, e) {
|
|
|
9
10
|
}
|
|
10
11
|
return t;
|
|
11
12
|
};
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
// استایل پایه برای input
|
|
16
|
-
const baseInputStyle = {
|
|
17
|
-
border: '1px solid #ccc',
|
|
18
|
-
borderRadius: '4px',
|
|
19
|
-
};
|
|
13
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
14
|
+
const jsx_runtime_1 = require("react/jsx-runtime");
|
|
15
|
+
const usePersianNumberInput_1 = require("../hooks/usePersianNumberInput");
|
|
20
16
|
const PersianNumberInput = (_a) => {
|
|
21
|
-
var {
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
}
|
|
34
|
-
//
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
17
|
+
var {
|
|
18
|
+
// جدا کردن آپشن های هوک از بقیه پراپ های input
|
|
19
|
+
initialValue, separatorCount, separatorChar, locale, maxDecimals, showZero, onValueChange, min, max } = _a,
|
|
20
|
+
// بقیه پراپ ها (مثل className, style, placeholder, id و ...) به input اصلی منتقل می شوند
|
|
21
|
+
restInputProps = __rest(_a, ["initialValue", "separatorCount", "separatorChar", "locale", "maxDecimals", "showZero", "onValueChange", "min", "max"]);
|
|
22
|
+
// اعتبارسنجی پراپها
|
|
23
|
+
if (maxDecimals !== undefined && maxDecimals < 0) {
|
|
24
|
+
console.warn('maxDecimals باید غیرمنفی باشد');
|
|
25
|
+
maxDecimals = 0;
|
|
26
|
+
}
|
|
27
|
+
if (min !== undefined && max !== undefined && min > max) {
|
|
28
|
+
console.warn('min نباید بزرگتر از max باشد');
|
|
29
|
+
}
|
|
30
|
+
const { value: formattedValue, onChange, rawValue, // می توانید rawValue را هم برگردانید اگر لازم است
|
|
31
|
+
} = (0, usePersianNumberInput_1.usePersianNumberInput)({
|
|
32
|
+
initialValue,
|
|
33
|
+
separatorCount,
|
|
34
|
+
separatorChar,
|
|
35
|
+
locale,
|
|
36
|
+
maxDecimals,
|
|
37
|
+
showZero,
|
|
38
|
+
onValueChange,
|
|
39
|
+
min,
|
|
40
|
+
max
|
|
41
|
+
});
|
|
42
|
+
return ((0, jsx_runtime_1.jsx)("input", Object.assign({ type: "text" // یا "tel" هم گاهی استفاده می شود
|
|
43
|
+
, inputMode: "decimal", dir: "ltr" // معمولا برای اعداد بهتر است
|
|
44
|
+
}, restInputProps, { value: formattedValue, onChange: onChange })));
|
|
42
45
|
};
|
|
43
|
-
|
|
46
|
+
exports.default = PersianNumberInput;
|
|
44
47
|
//# sourceMappingURL=PersianNumberInput.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"PersianNumberInput.js","sourceRoot":"","sources":["../../src/components/PersianNumberInput.tsx"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"PersianNumberInput.js","sourceRoot":"","sources":["../../src/components/PersianNumberInput.tsx"],"names":[],"mappings":";;;;;;;;;;;;;;AACA,0EAAuE;AAcvE,MAAM,kBAAkB,GAAsC,CAAC,EAa9D,EAAE,EAAE;QAb0D;IAC3D,+CAA+C;IAC/C,YAAY,EACZ,cAAc,EACd,aAAa,EACb,MAAM,EACN,WAAW,EACX,QAAQ,EACR,aAAa,EACb,GAAG,EACH,GAAG,OAGN;IAFG,yFAAyF;IACtF,cAAc,cAZ0C,uHAa9D,CADoB;IAEjB,qBAAqB;IACrB,IAAI,WAAW,KAAK,SAAS,IAAI,WAAW,GAAG,CAAC,EAAE,CAAC;QAC/C,OAAO,CAAC,IAAI,CAAC,+BAA+B,CAAC,CAAC;QAC9C,WAAW,GAAG,CAAC,CAAC;IACpB,CAAC;IACD,IAAI,GAAG,KAAK,SAAS,IAAI,GAAG,KAAK,SAAS,IAAI,GAAG,GAAG,GAAG,EAAE,CAAC;QACtD,OAAO,CAAC,IAAI,CAAC,+BAA+B,CAAC,CAAC;IAClD,CAAC;IAED,MAAM,EACF,KAAK,EAAE,cAAc,EACrB,QAAQ,EACR,QAAQ,EAAE,kDAAkD;MAC/D,GAAG,IAAA,6CAAqB,EAAC;QACtB,YAAY;QACZ,cAAc;QACd,aAAa;QACb,MAAM;QACN,WAAW;QACX,QAAQ;QACR,aAAa;QACb,GAAG;QACH,GAAG;KACN,CAAC,CAAC;IAEH,OAAO,CACH,gDACI,IAAI,EAAC,MAAM,CAAC,kCAAkC;UAC9C,SAAS,EAAC,SAAS,EACnB,GAAG,EAAC,KAAK,CAAC,6BAA6B;QACnC,cAAc,IAClB,KAAK,EAAE,cAAc,EACrB,QAAQ,EAAE,QAAQ,IACpB,CACL,CAAC;AACN,CAAC,CAAC;AAEF,kBAAe,kBAAkB,CAAC"}
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { TransformNumberOptions } from '../utils/transformNumber';
|
|
3
|
+
interface UsePersianNumberInputProps extends TransformNumberOptions {
|
|
4
|
+
initialValue?: number | string;
|
|
5
|
+
onValueChange?: (value: string | undefined) => void;
|
|
6
|
+
min?: number;
|
|
7
|
+
max?: number;
|
|
8
|
+
}
|
|
9
|
+
interface UsePersianNumberInputReturn {
|
|
10
|
+
/** مقدار فرمت شده برای نمایش در input. */
|
|
11
|
+
value: string;
|
|
12
|
+
/** تابع onChange برای اتصال به input. */
|
|
13
|
+
onChange: (event: React.ChangeEvent<HTMLInputElement>) => void;
|
|
14
|
+
/** تابع برای تنظیم مقدار به صورت برنامه نویسی (مقدار عددی تمیز). */
|
|
15
|
+
setValue: (newValue: number | string | undefined) => void;
|
|
16
|
+
/** مقدار عددی خام (رشته انگلیسی تمیز شده) */
|
|
17
|
+
rawValue: string | undefined;
|
|
18
|
+
}
|
|
19
|
+
export declare const usePersianNumberInput: ({ initialValue, separatorCount, separatorChar, locale, maxDecimals, showZero, onValueChange, min, max, }?: UsePersianNumberInputProps) => UsePersianNumberInputReturn;
|
|
20
|
+
export {};
|
|
21
|
+
//# sourceMappingURL=usePersianNumberInput.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"usePersianNumberInput.d.ts","sourceRoot":"","sources":["../../src/hooks/usePersianNumberInput.ts"],"names":[],"mappings":"AAAA,OAAO,KAAyC,MAAM,OAAO,CAAC;AAE9D,OAAO,EAAmB,sBAAsB,EAAE,MAAM,0BAA0B,CAAC;AAGnF,UAAU,0BAA2B,SAAQ,sBAAsB;IACjE,YAAY,CAAC,EAAE,MAAM,GAAG,MAAM,CAAC;IAC/B,aAAa,CAAC,EAAE,CAAC,KAAK,EAAE,MAAM,GAAG,SAAS,KAAK,IAAI,CAAC;IACpD,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,GAAG,CAAC,EAAE,MAAM,CAAC;CACd;AAED,UAAU,2BAA2B;IACnC,0CAA0C;IAC1C,KAAK,EAAE,MAAM,CAAC;IACd,yCAAyC;IACzC,QAAQ,EAAE,CAAC,KAAK,EAAE,KAAK,CAAC,WAAW,CAAC,gBAAgB,CAAC,KAAK,IAAI,CAAC;IAC/D,oEAAoE;IACpE,QAAQ,EAAE,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,GAAG,SAAS,KAAK,IAAI,CAAC;IAC1D,6CAA6C;IAC7C,QAAQ,EAAE,MAAM,GAAG,SAAS,CAAC;CAC9B;AAWD,eAAO,MAAM,qBAAqB,GAAI,2GAUnC,0BAA+B,KAAG,2BAqIpC,CAAC"}
|
|
@@ -0,0 +1,139 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
exports.usePersianNumberInput = void 0;
|
|
7
|
+
const react_1 = require("react");
|
|
8
|
+
const decimal_js_1 = __importDefault(require("decimal.js"));
|
|
9
|
+
const transformNumber_1 = require("../utils/transformNumber");
|
|
10
|
+
const digitUtils_1 = require("../utils/digitUtils");
|
|
11
|
+
// تابع کمکی برای گرد کردن مقدار به تعداد اعشار مشخص
|
|
12
|
+
const roundToDecimals = (value, maxDecimals) => {
|
|
13
|
+
if (!value || !value.includes('.'))
|
|
14
|
+
return value; // اگر اعشاری نیست یا خالی است، همان را برگردان
|
|
15
|
+
const [integerPart, fractionalPart] = value.split('.');
|
|
16
|
+
if (maxDecimals === 0)
|
|
17
|
+
return integerPart; // اگر اعشار مجاز نیست، فقط بخش صحیح
|
|
18
|
+
const trimmedFractional = fractionalPart.slice(0, maxDecimals);
|
|
19
|
+
return trimmedFractional ? `${integerPart}.${trimmedFractional}` : integerPart;
|
|
20
|
+
};
|
|
21
|
+
const usePersianNumberInput = ({ initialValue, separatorCount = 3, separatorChar = ',', locale = 'fa', maxDecimals = 0, showZero = false, onValueChange, min, max, } = {}) => {
|
|
22
|
+
// State داخلی برای نگه داشتن مقدار عددی *تمیز شده* (ارقام انگلیسی، بدون جداکننده)
|
|
23
|
+
const [rawValue, setRawValue] = (0, react_1.useState)(() => {
|
|
24
|
+
if (initialValue === null || initialValue === undefined)
|
|
25
|
+
return undefined;
|
|
26
|
+
// مقدار اولیه را پاکسازی کن
|
|
27
|
+
let sanitized = (0, digitUtils_1.sanitizeNumericInput)(String(initialValue));
|
|
28
|
+
// اگر مقدار اولیه 0 بود و showZero false بود، مقدار خام را undefined بگذار
|
|
29
|
+
if (parseFloat(sanitized) === 0 &&
|
|
30
|
+
!showZero &&
|
|
31
|
+
initialValue !== 0 &&
|
|
32
|
+
initialValue !== '0') {
|
|
33
|
+
return undefined;
|
|
34
|
+
}
|
|
35
|
+
// گرد کردن به تعداد اعشار مجاز
|
|
36
|
+
sanitized = roundToDecimals(sanitized, maxDecimals);
|
|
37
|
+
// بررسی min و max برای مقدار اولیه
|
|
38
|
+
if (sanitized) {
|
|
39
|
+
try {
|
|
40
|
+
const numericValue = new decimal_js_1.default(sanitized);
|
|
41
|
+
if ((min !== undefined && numericValue.lt(min)) ||
|
|
42
|
+
(max !== undefined && numericValue.gt(max))) {
|
|
43
|
+
return undefined; // اگر مقدار اولیه خارج از محدوده است، undefined برگردان
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
catch (error) {
|
|
47
|
+
console.warn(`Invalid initial value: ${sanitized}`, error);
|
|
48
|
+
return undefined; // در صورت خطا، مقدار نامعتبر را رد کن
|
|
49
|
+
}
|
|
50
|
+
}
|
|
51
|
+
return sanitized || undefined; // اگر پاکسازی نتیجه خالی داد، undefined بگذار
|
|
52
|
+
});
|
|
53
|
+
// استفاده از useMemo برای بهینه سازی
|
|
54
|
+
const displayValue = (0, react_1.useMemo)(() => {
|
|
55
|
+
const options = { separatorCount, separatorChar, locale, maxDecimals, showZero };
|
|
56
|
+
// اگر rawValue تعریف نشده باشد، "" برگردان
|
|
57
|
+
if (rawValue === undefined) {
|
|
58
|
+
return showZero ? (0, transformNumber_1.transformNumber)('0', options) : '';
|
|
59
|
+
}
|
|
60
|
+
return (0, transformNumber_1.transformNumber)(rawValue, options);
|
|
61
|
+
}, [rawValue, separatorCount, separatorChar, locale, maxDecimals, showZero]);
|
|
62
|
+
const handleChange = (0, react_1.useCallback)((event) => {
|
|
63
|
+
const inputValue = event.target.value;
|
|
64
|
+
let sanitizedValue = (0, digitUtils_1.sanitizeNumericInput)(inputValue); // پاکسازی ورودی کاربر
|
|
65
|
+
// اگر مقدار پاکسازی شده با مقدار خام فعلی متفاوت بود، آپدیت کن
|
|
66
|
+
if (sanitizedValue !== rawValue) {
|
|
67
|
+
// گرد کردن به تعداد اعشار مجاز
|
|
68
|
+
sanitizedValue = roundToDecimals(sanitizedValue, maxDecimals);
|
|
69
|
+
// بررسی min و max
|
|
70
|
+
let valueToSet = sanitizedValue;
|
|
71
|
+
if (sanitizedValue) {
|
|
72
|
+
try {
|
|
73
|
+
const numericValue = new decimal_js_1.default(sanitizedValue);
|
|
74
|
+
if ((min !== undefined && numericValue.lt(min)) ||
|
|
75
|
+
(max !== undefined && numericValue.gt(max))) {
|
|
76
|
+
return; // اگر مقدار خارج از محدوده است، تغییر را اعمال نکن
|
|
77
|
+
}
|
|
78
|
+
}
|
|
79
|
+
catch (error) {
|
|
80
|
+
console.warn(`Invalid input value: ${sanitizedValue}`, error);
|
|
81
|
+
return; // در صورت خطا، مقدار نامعتبر را رد کن
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
// اگر مقدار پاکسازی شده 0 بود و showZero=false، مقدار خام را undefined بگذار
|
|
85
|
+
valueToSet =
|
|
86
|
+
parseFloat(sanitizedValue) === 0 &&
|
|
87
|
+
!showZero &&
|
|
88
|
+
sanitizedValue !== '0.'
|
|
89
|
+
? undefined
|
|
90
|
+
: sanitizedValue;
|
|
91
|
+
setRawValue(valueToSet);
|
|
92
|
+
if (onValueChange) {
|
|
93
|
+
onValueChange(valueToSet); // اطلاع رسانی مقدار عددی تمیز شده
|
|
94
|
+
}
|
|
95
|
+
}
|
|
96
|
+
}, [rawValue, onValueChange, showZero, min, max, maxDecimals]);
|
|
97
|
+
const handleSetValue = (0, react_1.useCallback)((newValue) => {
|
|
98
|
+
if (newValue === null || newValue === undefined) {
|
|
99
|
+
setRawValue(undefined);
|
|
100
|
+
if (onValueChange)
|
|
101
|
+
onValueChange(undefined);
|
|
102
|
+
return;
|
|
103
|
+
}
|
|
104
|
+
let sanitizedValue = (0, digitUtils_1.sanitizeNumericInput)(String(newValue));
|
|
105
|
+
// گرد کردن به تعداد اعشار مجاز
|
|
106
|
+
sanitizedValue = roundToDecimals(sanitizedValue, maxDecimals);
|
|
107
|
+
// بررسی min و max
|
|
108
|
+
if (sanitizedValue) {
|
|
109
|
+
try {
|
|
110
|
+
const numericValue = new decimal_js_1.default(sanitizedValue);
|
|
111
|
+
if ((min !== undefined && numericValue.lt(min)) ||
|
|
112
|
+
(max !== undefined && numericValue.gt(max))) {
|
|
113
|
+
return; // اگر مقدار خارج از محدوده است، تغییر را اعمال نکن
|
|
114
|
+
}
|
|
115
|
+
}
|
|
116
|
+
catch (error) {
|
|
117
|
+
console.warn(`Invalid set value: ${sanitizedValue}`, error);
|
|
118
|
+
return; // در صورت خطا، مقدار نامعتبر را رد کن
|
|
119
|
+
}
|
|
120
|
+
}
|
|
121
|
+
const valueToSet = parseFloat(sanitizedValue) === 0 &&
|
|
122
|
+
!showZero &&
|
|
123
|
+
sanitizedValue !== '0.'
|
|
124
|
+
? undefined
|
|
125
|
+
: sanitizedValue;
|
|
126
|
+
setRawValue(valueToSet);
|
|
127
|
+
if (onValueChange) {
|
|
128
|
+
onValueChange(valueToSet);
|
|
129
|
+
}
|
|
130
|
+
}, [onValueChange, showZero, min, max, maxDecimals]);
|
|
131
|
+
return {
|
|
132
|
+
value: displayValue, // مقدار قالب بندی شده برای input
|
|
133
|
+
onChange: handleChange, // تابع برای اتصال به input.onChange
|
|
134
|
+
setValue: handleSetValue, // تابع برای تنظیم مقدار برنامه ای
|
|
135
|
+
rawValue: rawValue, // مقدار عددی خام (رشته انگلیسی)
|
|
136
|
+
};
|
|
137
|
+
};
|
|
138
|
+
exports.usePersianNumberInput = usePersianNumberInput;
|
|
139
|
+
//# sourceMappingURL=usePersianNumberInput.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"usePersianNumberInput.js","sourceRoot":"","sources":["../../src/hooks/usePersianNumberInput.ts"],"names":[],"mappings":"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"}
|
package/dist/index.d.ts
CHANGED
|
@@ -1 +1,6 @@
|
|
|
1
|
+
export { usePersianNumberInput } from "./hooks/usePersianNumberInput";
|
|
1
2
|
export { default as PersianNumberInput } from "./components/PersianNumberInput";
|
|
3
|
+
export { transformNumber } from "./utils/transformNumber";
|
|
4
|
+
export type { TransformNumberOptions } from "./utils/transformNumber";
|
|
5
|
+
export * from "./utils/digitUtils";
|
|
6
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,qBAAqB,EAAE,MAAM,+BAA+B,CAAC;AACtE,OAAO,EAAE,OAAO,IAAI,kBAAkB,EAAE,MAAM,iCAAiC,CAAC;AAChF,OAAO,EAAE,eAAe,EAAE,MAAM,yBAAyB,CAAC;AAC1D,YAAY,EAAE,sBAAsB,EAAE,MAAM,yBAAyB,CAAC;AACtE,cAAc,oBAAoB,CAAC"}
|
package/dist/index.js
CHANGED
|
@@ -1,2 +1,28 @@
|
|
|
1
|
-
|
|
1
|
+
"use strict";
|
|
2
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
3
|
+
if (k2 === undefined) k2 = k;
|
|
4
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
5
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
6
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
7
|
+
}
|
|
8
|
+
Object.defineProperty(o, k2, desc);
|
|
9
|
+
}) : (function(o, m, k, k2) {
|
|
10
|
+
if (k2 === undefined) k2 = k;
|
|
11
|
+
o[k2] = m[k];
|
|
12
|
+
}));
|
|
13
|
+
var __exportStar = (this && this.__exportStar) || function(m, exports) {
|
|
14
|
+
for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
|
|
15
|
+
};
|
|
16
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
17
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
18
|
+
};
|
|
19
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
20
|
+
exports.transformNumber = exports.PersianNumberInput = exports.usePersianNumberInput = void 0;
|
|
21
|
+
var usePersianNumberInput_1 = require("./hooks/usePersianNumberInput");
|
|
22
|
+
Object.defineProperty(exports, "usePersianNumberInput", { enumerable: true, get: function () { return usePersianNumberInput_1.usePersianNumberInput; } });
|
|
23
|
+
var PersianNumberInput_1 = require("./components/PersianNumberInput");
|
|
24
|
+
Object.defineProperty(exports, "PersianNumberInput", { enumerable: true, get: function () { return __importDefault(PersianNumberInput_1).default; } });
|
|
25
|
+
var transformNumber_1 = require("./utils/transformNumber");
|
|
26
|
+
Object.defineProperty(exports, "transformNumber", { enumerable: true, get: function () { return transformNumber_1.transformNumber; } });
|
|
27
|
+
__exportStar(require("./utils/digitUtils"), exports);
|
|
2
28
|
//# sourceMappingURL=index.js.map
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;AAAA,uEAAsE;AAA7D,8HAAA,qBAAqB,OAAA;AAC9B,sEAAgF;AAAvE,yIAAA,OAAO,OAAsB;AACtC,2DAA0D;AAAjD,kHAAA,eAAe,OAAA;AAExB,qDAAmC"}
|
|
@@ -1,6 +1,48 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* نقشه ارقام محلی برای زبانهای مختلف.
|
|
3
|
+
*/
|
|
1
4
|
export declare const digitsMap: {
|
|
2
|
-
[key: string]: string
|
|
5
|
+
[key: string]: ReadonlyArray<string>;
|
|
3
6
|
};
|
|
4
|
-
|
|
5
|
-
|
|
7
|
+
/**
|
|
8
|
+
* نقشه جداکننده اعشار برای زبانهای مختلف.
|
|
9
|
+
*/
|
|
10
|
+
export declare const decimalSeparatorMap: {
|
|
11
|
+
[key: string]: string;
|
|
12
|
+
};
|
|
13
|
+
/**
|
|
14
|
+
* تبدیل رشته حاوی ارقام محلی (مانند فارسی) به رشته با ارقام انگلیسی (0-9).
|
|
15
|
+
* @param str رشته ورودی
|
|
16
|
+
* @returns رشته با ارقام انگلیسی
|
|
17
|
+
*/
|
|
6
18
|
export declare const convertToEnglishDigits: (str: string) => string;
|
|
19
|
+
/**
|
|
20
|
+
* تبدیل رشته حاوی ارقام انگلیسی (0-9) به رشته با ارقام محلی.
|
|
21
|
+
* @param numStr رشته با ارقام انگلیسی
|
|
22
|
+
* @param locale کد زبان ('fa', 'in', ...)
|
|
23
|
+
* @returns رشته با ارقام محلی
|
|
24
|
+
*/
|
|
25
|
+
export declare const toLocalizedDigits: (numStr: string, locale: keyof typeof digitsMap) => string;
|
|
26
|
+
/**
|
|
27
|
+
* جایگزینی جداکننده اعشار انگلیسی (.) با جداکننده محلی.
|
|
28
|
+
* @param numStr رشته با ارقام و جداکننده انگلیسی
|
|
29
|
+
* @param locale کد زبان
|
|
30
|
+
* @returns رشته با جداکننده اعشار محلی
|
|
31
|
+
*/
|
|
32
|
+
export declare const localizeDecimalSeparator: (numStr: string, locale: keyof typeof decimalSeparatorMap) => string;
|
|
33
|
+
/**
|
|
34
|
+
* گروهبندی ارقام قسمت صحیح یک عدد با استفاده از جداکننده.
|
|
35
|
+
* @param numStr قسمت صحیح عدد (فقط ارقام انگلیسی)
|
|
36
|
+
* @param separatorCount تعداد ارقام در هر گروه (مثلا 3 برای هزارگان)
|
|
37
|
+
* @param separatorChar کاراکتر جداکننده (پیش فرض ',')
|
|
38
|
+
* @returns رشته گروهبندی شده
|
|
39
|
+
*/
|
|
40
|
+
export declare const groupDigits: (numStr: string, separatorCount: number, separatorChar?: string) => string;
|
|
41
|
+
/**
|
|
42
|
+
* پاکسازی ورودی کاربر برای نگه داشتن فقط کاراکترهای عددی معتبر (ارقام، یک نقطه، یک علامت منفی در ابتدا).
|
|
43
|
+
* ابتدا ارقام محلی را به انگلیسی تبدیل می کند.
|
|
44
|
+
* @param value مقدار ورودی کاربر
|
|
45
|
+
* @returns رشته عددی پاکسازی شده با ارقام انگلیسی
|
|
46
|
+
*/
|
|
47
|
+
export declare const sanitizeNumericInput: (value: string) => string;
|
|
48
|
+
//# sourceMappingURL=digitUtils.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"digitUtils.d.ts","sourceRoot":"","sources":["../../src/utils/digitUtils.ts"],"names":[],"mappings":"AAEA;;GAEG;AACH,eAAO,MAAM,SAAS,EAAE;IAAE,CAAC,GAAG,EAAE,MAAM,GAAG,aAAa,CAAC,MAAM,CAAC,CAAA;CAI7D,CAAC;AAEF;;GAEG;AACH,eAAO,MAAM,mBAAmB,EAAE;IAAE,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,CAAA;CAGxD,CAAC;AAaF;;;;GAIG;AACH,eAAO,MAAM,sBAAsB,GAAI,KAAK,MAAM,KAAG,MAGpD,CAAC;AAEF;;;;;GAKG;AACH,eAAO,MAAM,iBAAiB,GAAI,QAAQ,MAAM,EAAE,QAAQ,MAAM,OAAO,SAAS,KAAG,MAIlF,CAAC;AAEF;;;;;GAKG;AACH,eAAO,MAAM,wBAAwB,GAAI,QAAQ,MAAM,EAAE,QAAQ,MAAM,OAAO,mBAAmB,KAAG,MAInG,CAAC;AAEF;;;;;;GAMG;AACH,eAAO,MAAM,WAAW,GACtB,QAAQ,MAAM,EACd,gBAAgB,MAAM,EACtB,sBAAmB,KAClB,MAOF,CAAC;AAEF;;;;;GAKG;AACH,eAAO,MAAM,oBAAoB,GAAI,OAAO,MAAM,KAAG,MAyBpD,CAAC"}
|
package/dist/utils/digitUtils.js
CHANGED
|
@@ -1,41 +1,110 @@
|
|
|
1
|
-
|
|
1
|
+
"use strict";
|
|
2
|
+
// utils/digitUtils.ts
|
|
3
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
4
|
+
exports.sanitizeNumericInput = exports.groupDigits = exports.localizeDecimalSeparator = exports.toLocalizedDigits = exports.convertToEnglishDigits = exports.decimalSeparatorMap = exports.digitsMap = void 0;
|
|
5
|
+
/**
|
|
6
|
+
* نقشه ارقام محلی برای زبانهای مختلف.
|
|
7
|
+
*/
|
|
8
|
+
exports.digitsMap = {
|
|
2
9
|
fa: ["۰", "۱", "۲", "۳", "۴", "۵", "۶", "۷", "۸", "۹"],
|
|
3
|
-
|
|
10
|
+
// می توانید زبان های دیگر را اضافه کنید
|
|
11
|
+
// in: ["०", "१", "२", "३", "४", "५", "६", "७", "८", "९"],
|
|
4
12
|
};
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
13
|
+
/**
|
|
14
|
+
* نقشه جداکننده اعشار برای زبانهای مختلف.
|
|
15
|
+
*/
|
|
16
|
+
exports.decimalSeparatorMap = {
|
|
17
|
+
fa: "٫",
|
|
18
|
+
// en: ".", (پیش فرض نقطه است)
|
|
8
19
|
};
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
20
|
+
const allLocalizedDigits = Object.values(exports.digitsMap).flat().join("");
|
|
21
|
+
const conversionMap = {};
|
|
22
|
+
for (const locale in exports.digitsMap) {
|
|
23
|
+
exports.digitsMap[locale].forEach((digit, index) => {
|
|
24
|
+
conversionMap[digit] = index.toString();
|
|
25
|
+
});
|
|
26
|
+
}
|
|
27
|
+
// Regex بهینه شده برای پیدا کردن تمام ارقام محلی
|
|
28
|
+
const localizedDigitsRegex = new RegExp(`[${allLocalizedDigits}]`, "g");
|
|
29
|
+
/**
|
|
30
|
+
* تبدیل رشته حاوی ارقام محلی (مانند فارسی) به رشته با ارقام انگلیسی (0-9).
|
|
31
|
+
* @param str رشته ورودی
|
|
32
|
+
* @returns رشته با ارقام انگلیسی
|
|
33
|
+
*/
|
|
34
|
+
const convertToEnglishDigits = (str) => {
|
|
35
|
+
if (!str)
|
|
36
|
+
return "";
|
|
37
|
+
return str.replace(localizedDigitsRegex, (char) => conversionMap[char] || char);
|
|
38
|
+
};
|
|
39
|
+
exports.convertToEnglishDigits = convertToEnglishDigits;
|
|
40
|
+
/**
|
|
41
|
+
* تبدیل رشته حاوی ارقام انگلیسی (0-9) به رشته با ارقام محلی.
|
|
42
|
+
* @param numStr رشته با ارقام انگلیسی
|
|
43
|
+
* @param locale کد زبان ('fa', 'in', ...)
|
|
44
|
+
* @returns رشته با ارقام محلی
|
|
45
|
+
*/
|
|
46
|
+
const toLocalizedDigits = (numStr, locale) => {
|
|
47
|
+
if (!numStr || !exports.digitsMap[locale])
|
|
48
|
+
return numStr;
|
|
49
|
+
const localeDigits = exports.digitsMap[locale];
|
|
50
|
+
return numStr.replace(/\d/g, (digit) => localeDigits[parseInt(digit)]);
|
|
51
|
+
};
|
|
52
|
+
exports.toLocalizedDigits = toLocalizedDigits;
|
|
53
|
+
/**
|
|
54
|
+
* جایگزینی جداکننده اعشار انگلیسی (.) با جداکننده محلی.
|
|
55
|
+
* @param numStr رشته با ارقام و جداکننده انگلیسی
|
|
56
|
+
* @param locale کد زبان
|
|
57
|
+
* @returns رشته با جداکننده اعشار محلی
|
|
58
|
+
*/
|
|
59
|
+
const localizeDecimalSeparator = (numStr, locale) => {
|
|
60
|
+
const separator = exports.decimalSeparatorMap[locale];
|
|
61
|
+
if (!separator)
|
|
62
|
+
return numStr; // اگر جداکننده محلی تعریف نشده، همان نقطه را برگردان
|
|
63
|
+
return numStr.replace(".", separator);
|
|
64
|
+
};
|
|
65
|
+
exports.localizeDecimalSeparator = localizeDecimalSeparator;
|
|
66
|
+
/**
|
|
67
|
+
* گروهبندی ارقام قسمت صحیح یک عدد با استفاده از جداکننده.
|
|
68
|
+
* @param numStr قسمت صحیح عدد (فقط ارقام انگلیسی)
|
|
69
|
+
* @param separatorCount تعداد ارقام در هر گروه (مثلا 3 برای هزارگان)
|
|
70
|
+
* @param separatorChar کاراکتر جداکننده (پیش فرض ',')
|
|
71
|
+
* @returns رشته گروهبندی شده
|
|
72
|
+
*/
|
|
73
|
+
const groupDigits = (numStr, separatorCount, separatorChar = ",") => {
|
|
74
|
+
if (!numStr || separatorCount <= 0) {
|
|
75
|
+
return numStr;
|
|
12
76
|
}
|
|
13
|
-
|
|
77
|
+
// Regex برای پیدا کردن محل درج جداکننده ها (از راست به چپ)
|
|
78
|
+
const regex = new RegExp(`\\B(?=(\\d{${separatorCount}})+(?!\\d))`, "g");
|
|
79
|
+
return numStr.replace(regex, separatorChar);
|
|
14
80
|
};
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
81
|
+
exports.groupDigits = groupDigits;
|
|
82
|
+
/**
|
|
83
|
+
* پاکسازی ورودی کاربر برای نگه داشتن فقط کاراکترهای عددی معتبر (ارقام، یک نقطه، یک علامت منفی در ابتدا).
|
|
84
|
+
* ابتدا ارقام محلی را به انگلیسی تبدیل می کند.
|
|
85
|
+
* @param value مقدار ورودی کاربر
|
|
86
|
+
* @returns رشته عددی پاکسازی شده با ارقام انگلیسی
|
|
87
|
+
*/
|
|
88
|
+
const sanitizeNumericInput = (value) => {
|
|
89
|
+
if (value === null || value === undefined)
|
|
90
|
+
return "";
|
|
91
|
+
// 1. تبدیل همه ارقام به انگلیسی
|
|
92
|
+
let cleaned = (0, exports.convertToEnglishDigits)(String(value));
|
|
93
|
+
// 2. حذف همه چیز به جز ارقام، نقطه و علامت منفی
|
|
94
|
+
cleaned = cleaned.replace(/[^-0-9.]/g, "");
|
|
95
|
+
// 3. مدیریت علامت منفی: فقط یکی در ابتدا مجاز است
|
|
96
|
+
const negativeSign = cleaned.startsWith("-") ? "-" : "";
|
|
97
|
+
cleaned = cleaned.replace(/-/g, ""); // حذف همه منفی ها
|
|
98
|
+
// 4. مدیریت نقطه اعشار: فقط یکی مجاز است
|
|
99
|
+
const parts = cleaned.split(".");
|
|
100
|
+
let integerPart = parts[0] || ""; // بخش صحیح
|
|
101
|
+
let fractionalPart = parts.slice(1).join(""); // فقط اولین بخش اعشاری را نگه دار
|
|
102
|
+
// 5. بازسازی رشته تمیز شده
|
|
103
|
+
let sanitized = negativeSign + integerPart;
|
|
104
|
+
if (parts.length > 1) { // اگر نقطه ای وجود داشت
|
|
105
|
+
sanitized += "." + fractionalPart;
|
|
106
|
+
}
|
|
107
|
+
return sanitized;
|
|
40
108
|
};
|
|
109
|
+
exports.sanitizeNumericInput = sanitizeNumericInput;
|
|
41
110
|
//# sourceMappingURL=digitUtils.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"digitUtils.js","sourceRoot":"","sources":["../../src/utils/digitUtils.ts"],"names":[],"mappings":"AAAA,
|
|
1
|
+
{"version":3,"file":"digitUtils.js","sourceRoot":"","sources":["../../src/utils/digitUtils.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
export interface TransformNumberOptions {
|
|
2
|
+
/** تعداد ارقام در هر گروه برای جداسازی (مثلا 3). 0 یا کمتر یعنی بدون جداسازی. */
|
|
3
|
+
separatorCount?: number;
|
|
4
|
+
/** کاراکتر جداکننده گروه ها (پیش فرض ','). */
|
|
5
|
+
separatorChar?: string;
|
|
6
|
+
/** کد زبان برای نمایش ارقام ('fa', 'en', ...). پیش فرض 'fa'. */
|
|
7
|
+
locale?: 'fa' | 'en' | string;
|
|
8
|
+
/** حداکثر تعداد ارقام اعشار مجاز. 0 یعنی بدون اعشار. */
|
|
9
|
+
maxDecimals?: number;
|
|
10
|
+
/** اگر true باشد، حتی اگر مقدار ورودی 0 باشد، آن را نمایش بده. پیش فرض false */
|
|
11
|
+
showZero?: boolean;
|
|
12
|
+
}
|
|
13
|
+
/**
|
|
14
|
+
* یک عدد یا رشته عددی را به فرمت محلی و گروه بندی شده تبدیل می کند.
|
|
15
|
+
*
|
|
16
|
+
* @param input عدد یا رشته ورودی. می تواند شامل ارقام محلی یا انگلیسی باشد.
|
|
17
|
+
* @param options تنظیمات قالب بندی.
|
|
18
|
+
* @returns رشته قالب بندی شده یا رشته خالی اگر ورودی نامعتبر یا صفر (و showZero=false) باشد.
|
|
19
|
+
*/
|
|
20
|
+
export declare const transformNumber: (input: number | string | null | undefined, options?: TransformNumberOptions) => string;
|
|
21
|
+
//# sourceMappingURL=transformNumber.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"transformNumber.d.ts","sourceRoot":"","sources":["../../src/utils/transformNumber.ts"],"names":[],"mappings":"AASA,MAAM,WAAW,sBAAsB;IACrC,iFAAiF;IACjF,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,8CAA8C;IAC9C,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,gEAAgE;IAChE,MAAM,CAAC,EAAE,IAAI,GAAG,IAAI,GAAG,MAAM,CAAC;IAC9B,wDAAwD;IACxD,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,gFAAgF;IAChF,QAAQ,CAAC,EAAE,OAAO,CAAC;CACpB;AAED;;;;;;GAMG;AACH,eAAO,MAAM,eAAe,GAC1B,OAAO,MAAM,GAAG,MAAM,GAAG,IAAI,GAAG,SAAS,EACzC,UAAU,sBAAsB,KAC/B,MA6EF,CAAC"}
|
|
@@ -0,0 +1,77 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.transformNumber = void 0;
|
|
4
|
+
// utils/transformNumber.ts
|
|
5
|
+
const digitUtils_1 = require("./digitUtils");
|
|
6
|
+
/**
|
|
7
|
+
* یک عدد یا رشته عددی را به فرمت محلی و گروه بندی شده تبدیل می کند.
|
|
8
|
+
*
|
|
9
|
+
* @param input عدد یا رشته ورودی. می تواند شامل ارقام محلی یا انگلیسی باشد.
|
|
10
|
+
* @param options تنظیمات قالب بندی.
|
|
11
|
+
* @returns رشته قالب بندی شده یا رشته خالی اگر ورودی نامعتبر یا صفر (و showZero=false) باشد.
|
|
12
|
+
*/
|
|
13
|
+
const transformNumber = (input, options) => {
|
|
14
|
+
const { separatorCount = 3, // پیش فرض 3 برای هزارگان
|
|
15
|
+
separatorChar = ',', locale = 'fa', maxDecimals = 0, showZero = false, // به طور پیش فرض صفر نمایش داده نشود مگر اینکه صریحا خواسته شود
|
|
16
|
+
} = options || {};
|
|
17
|
+
if (input === null || input === undefined || input === "") {
|
|
18
|
+
return showZero ? (0, digitUtils_1.toLocalizedDigits)("0", locale) : ""; // اگر ورودی خالی است و showZero=false، خالی برگردان
|
|
19
|
+
}
|
|
20
|
+
// 1. تبدیل ورودی به رشته و سپس به ارقام انگلیسی و پاکسازی اولیه
|
|
21
|
+
// توجه: در استفاده با input، بهتر است sanitizeNumericInput روی مقدار input *قبل* از پاس دادن به این تابع اجرا شود.
|
|
22
|
+
// اما برای اطمینان، اینجا هم یک تبدیل اولیه انجام می دهیم.
|
|
23
|
+
let str = (0, digitUtils_1.convertToEnglishDigits)(String(input));
|
|
24
|
+
// 2. بررسی اولیه برای معتبر بودن فرمت عددی (اختیاری اما مفید)
|
|
25
|
+
// این regex اجازه یک منفی در ابتدا و یک نقطه اعشار را می دهد.
|
|
26
|
+
if (!/^-?\d*(\.\d*)?$/.test(str)) {
|
|
27
|
+
// اگر فرمت پایه عددی نیست (بعد از تبدیل به انگلیسی)، یا خالی برگردان یا خود ورودی اصلی
|
|
28
|
+
// تصمیم: فعلا خالی بر میگردانیم یا صفر اگر showZero فعال باشد
|
|
29
|
+
console.warn(`Invalid numeric string after conversion: "${str}" from input: "${input}"`);
|
|
30
|
+
return showZero ? (0, digitUtils_1.toLocalizedDigits)("0", locale) : "";
|
|
31
|
+
}
|
|
32
|
+
// تبدیل رشته خالی یا فقط "-" به صفر اگر showZero فعال باشد
|
|
33
|
+
if ((str === "" || str === "-") && showZero) {
|
|
34
|
+
str = "0";
|
|
35
|
+
}
|
|
36
|
+
else if (str === "" || str === "-") {
|
|
37
|
+
return ""; // اگر ورودی فقط "-" بود یا خالی شد، خالی برگردان
|
|
38
|
+
}
|
|
39
|
+
// اگر ورودی فقط "." بود
|
|
40
|
+
if (str === ".") {
|
|
41
|
+
return showZero ? (0, digitUtils_1.toLocalizedDigits)("0", locale) : "۰"; // یا شاید "۰." ؟ تصمیم با شماست. نمایش صفر منطقی تر است.
|
|
42
|
+
}
|
|
43
|
+
// 3. محدود کردن تعداد ارقام اعشار
|
|
44
|
+
let [integerPart, fractionalPart] = str.split('.');
|
|
45
|
+
integerPart = integerPart || "0"; // اگر ورودی مثل ".5" بود
|
|
46
|
+
if (fractionalPart !== undefined) {
|
|
47
|
+
if (maxDecimals > 0) {
|
|
48
|
+
fractionalPart = fractionalPart.slice(0, maxDecimals);
|
|
49
|
+
// اگر بعد از بریدن، قسمت اعشاری خالی شد، آن را حذف کن
|
|
50
|
+
str = fractionalPart ? `${integerPart}.${fractionalPart}` : integerPart;
|
|
51
|
+
}
|
|
52
|
+
else {
|
|
53
|
+
// اگر maxDecimals صفر است، قسمت اعشار را حذف کن
|
|
54
|
+
str = integerPart;
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
else {
|
|
58
|
+
str = integerPart; // قسمت اعشاری وجود نداشت
|
|
59
|
+
}
|
|
60
|
+
// 4. جداسازی ارقام قسمت صحیح
|
|
61
|
+
// دوباره استخراج بخش صحیح و اعشاری چون ممکن است در مرحله 3 تغییر کرده باشد
|
|
62
|
+
[integerPart, fractionalPart] = str.split('.');
|
|
63
|
+
integerPart = integerPart || "0"; // اطمینان مجدد برای حالت "."
|
|
64
|
+
const groupedInt = (0, digitUtils_1.groupDigits)(integerPart, separatorCount, separatorChar);
|
|
65
|
+
// 5. ترکیب مجدد قسمت صحیح و اعشاری (اگر وجود دارد)
|
|
66
|
+
let finalStr = fractionalPart !== undefined ? `${groupedInt}.${fractionalPart}` : groupedInt;
|
|
67
|
+
// 6. محلی سازی (اگر locale انگلیسی نیست)
|
|
68
|
+
if (locale && locale !== 'en') {
|
|
69
|
+
// 6.1 جایگزینی جداکننده اعشار انگلیسی با محلی (قبل از تبدیل ارقام)
|
|
70
|
+
finalStr = (0, digitUtils_1.localizeDecimalSeparator)(finalStr, locale);
|
|
71
|
+
// 6.2 تبدیل ارقام انگلیسی به محلی
|
|
72
|
+
finalStr = (0, digitUtils_1.toLocalizedDigits)(finalStr, locale); // cast لازم است چون locale ممکن است string باشد
|
|
73
|
+
}
|
|
74
|
+
return finalStr;
|
|
75
|
+
};
|
|
76
|
+
exports.transformNumber = transformNumber;
|
|
77
|
+
//# sourceMappingURL=transformNumber.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"transformNumber.js","sourceRoot":"","sources":["../../src/utils/transformNumber.ts"],"names":[],"mappings":";;;AAAA,2BAA2B;AAC3B,6CAKsB;AAgBtB;;;;;;GAMG;AACI,MAAM,eAAe,GAAG,CAC7B,KAAyC,EACzC,OAAgC,EACxB,EAAE;IACV,MAAM,EACJ,cAAc,GAAG,CAAC,EAAE,yBAAyB;IAC7C,aAAa,GAAG,GAAG,EACnB,MAAM,GAAG,IAAI,EACb,WAAW,GAAG,CAAC,EACf,QAAQ,GAAG,KAAK,EAAE,gEAAgE;MACnF,GAAG,OAAO,IAAI,EAAE,CAAC;IAElB,IAAI,KAAK,KAAK,IAAI,IAAI,KAAK,KAAK,SAAS,IAAI,KAAK,KAAK,EAAE,EAAE,CAAC;QAC1D,OAAO,QAAQ,CAAC,CAAC,CAAC,IAAA,8BAAiB,EAAC,GAAG,EAAE,MAAa,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,oDAAoD;IACpH,CAAC;IAED,gEAAgE;IAChE,sHAAsH;IACtH,8DAA8D;IAC9D,IAAI,GAAG,GAAG,IAAA,mCAAsB,EAAC,MAAM,CAAC,KAAK,CAAC,CAAC,CAAC;IAEhD,8DAA8D;IAC9D,iEAAiE;IACjE,IAAI,CAAC,iBAAiB,CAAC,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC;QAChC,uFAAuF;QACvF,8DAA8D;QAC9D,OAAO,CAAC,IAAI,CAAC,6CAA6C,GAAG,kBAAkB,KAAK,GAAG,CAAC,CAAC;QACzF,OAAO,QAAQ,CAAC,CAAC,CAAC,IAAA,8BAAiB,EAAC,GAAG,EAAE,MAAa,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;IAChE,CAAC;IAED,2DAA2D;IAC3D,IAAI,CAAC,GAAG,KAAK,EAAE,IAAI,GAAG,KAAK,GAAG,CAAC,IAAI,QAAQ,EAAE,CAAC;QAC1C,GAAG,GAAG,GAAG,CAAC;IACd,CAAC;SAAM,IAAI,GAAG,KAAK,EAAE,IAAI,GAAG,KAAK,GAAG,EAAE,CAAC;QACnC,OAAO,EAAE,CAAC,CAAC,iDAAiD;IAChE,CAAC;IAED,wBAAwB;IACxB,IAAI,GAAG,KAAK,GAAG,EAAE,CAAC;QACf,OAAO,QAAQ,CAAC,CAAC,CAAC,IAAA,8BAAiB,EAAC,GAAG,EAAE,MAAa,CAAC,CAAC,CAAC,CAAC,GAAG,CAAE,CAAC,yDAAyD;IAC5H,CAAC;IAGD,kCAAkC;IAClC,IAAI,CAAC,WAAW,EAAE,cAAc,CAAC,GAAG,GAAG,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;IACnD,WAAW,GAAG,WAAW,IAAI,GAAG,CAAC,CAAC,yBAAyB;IAE3D,IAAI,cAAc,KAAK,SAAS,EAAE,CAAC;QACjC,IAAI,WAAW,GAAG,CAAC,EAAE,CAAC;YACpB,cAAc,GAAG,cAAc,CAAC,KAAK,CAAC,CAAC,EAAE,WAAW,CAAC,CAAC;YACtD,sDAAsD;YACtD,GAAG,GAAG,cAAc,CAAC,CAAC,CAAC,GAAG,WAAW,IAAI,cAAc,EAAE,CAAC,CAAC,CAAC,WAAW,CAAC;QAC1E,CAAC;aAAM,CAAC;YACN,gDAAgD;YAChD,GAAG,GAAG,WAAW,CAAC;QACpB,CAAC;IACH,CAAC;SAAM,CAAC;QACN,GAAG,GAAG,WAAW,CAAC,CAAC,yBAAyB;IAC9C,CAAC;IAGD,6BAA6B;IAC7B,8EAA8E;IAC9E,CAAC,WAAW,EAAE,cAAc,CAAC,GAAG,GAAG,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;IAC/C,WAAW,GAAG,WAAW,IAAI,GAAG,CAAC,CAAC,6BAA6B;IAE/D,MAAM,UAAU,GAAG,IAAA,wBAAW,EAAC,WAAW,EAAE,cAAc,EAAE,aAAa,CAAC,CAAC;IAE3E,mDAAmD;IACnD,IAAI,QAAQ,GAAG,cAAc,KAAK,SAAS,CAAC,CAAC,CAAC,GAAG,UAAU,IAAI,cAAc,EAAE,CAAC,CAAC,CAAC,UAAU,CAAC;IAE7F,yCAAyC;IACzC,IAAI,MAAM,IAAI,MAAM,KAAK,IAAI,EAAE,CAAC;QAC5B,mEAAmE;QACnE,QAAQ,GAAG,IAAA,qCAAwB,EAAC,QAAQ,EAAE,MAAM,CAAC,CAAC;QACtD,kCAAkC;QAClC,QAAQ,GAAG,IAAA,8BAAiB,EAAC,QAAQ,EAAE,MAAa,CAAC,CAAC,CAAC,gDAAgD;IAC3G,CAAC;IAED,OAAO,QAAQ,CAAC;AAClB,CAAC,CAAC;AAhFW,QAAA,eAAe,mBAgF1B"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "persian-number-input",
|
|
3
|
-
"version": "
|
|
3
|
+
"version": "4.0.0",
|
|
4
4
|
"description": "React component for Persian, Indic, or English localized number input with customizable digit grouping",
|
|
5
5
|
"main": "dist/index.js",
|
|
6
6
|
"module": "dist/index.js",
|
|
@@ -47,6 +47,6 @@
|
|
|
47
47
|
"typescript": "^5.8.3"
|
|
48
48
|
},
|
|
49
49
|
"dependencies": {
|
|
50
|
-
"
|
|
50
|
+
"decimal.js": "^10.5.0"
|
|
51
51
|
}
|
|
52
52
|
}
|