nhb-toolbox 4.28.51 → 4.28.53

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/CHANGELOG.md CHANGED
@@ -4,6 +4,14 @@
4
4
 
5
5
  All notable changes to the package will be documented here.
6
6
 
7
+ ## [4.28.53] - 2026-01-01
8
+
9
+ - **Optimized** *internal utilities* to enhance **runtime performance** and **editor IntelliSense**.
10
+
11
+ ## [4.28.52] - 2025-12-30
12
+
13
+ - **Added** *new* methods for `BanglaCalendar`: `addDays`, `addWeeks`, `addMonths`, `addYears`, `valueOf` and `[Symbol.toPrimitive]`.
14
+
7
15
  ## [4.28.51] - 2025-12-24
8
16
 
9
17
  - **Removed** strictness from *format* parameter of `formatTimePart` utility and `Chronos.formatTimePart` static method.
@@ -1,4 +1,5 @@
1
1
  "use strict";
2
+ var _a;
2
3
  Object.defineProperty(exports, "__esModule", { value: true });
3
4
  exports.Bongabdo = exports.BnCalendar = exports.BanglaCalendar = void 0;
4
5
  const non_primitives_1 = require("../guards/non-primitives");
@@ -18,33 +19,33 @@ class BanglaCalendar {
18
19
  constructor(dateBnYrOrCfg, bnMonthOrCfg, bnDateOrCfg, config) {
19
20
  this.variant = this.#processVariants(dateBnYrOrCfg, bnMonthOrCfg, bnDateOrCfg, config);
20
21
  let date = dateBnYrOrCfg instanceof Date ? dateBnYrOrCfg : (new Date(((0, specials_1.isDateString)(dateBnYrOrCfg) &&
21
- !BanglaCalendar.isBanglaDateString(dateBnYrOrCfg)) ?
22
+ !_a.isBanglaDateString(dateBnYrOrCfg)) ?
22
23
  dateBnYrOrCfg
23
- : (0, primitives_1.isNumber)(dateBnYrOrCfg) && !BanglaCalendar.isBanglaYearEn(dateBnYrOrCfg) ?
24
+ : (0, primitives_1.isNumber)(dateBnYrOrCfg) && !_a.isBanglaYearEn(dateBnYrOrCfg) ?
24
25
  dateBnYrOrCfg
25
26
  : Date.now()));
26
27
  if (isNaN(date.getTime())) {
27
28
  date = new Date();
28
29
  }
29
30
  const { year, month, monthDate } = this.#processDate(date);
30
- let bnYear = BanglaCalendar.isBanglaYear(dateBnYrOrCfg) ? (0, convert_1.banglaToDigit)(dateBnYrOrCfg)
31
- : (0, primitives_1.isNumber)(dateBnYrOrCfg) && BanglaCalendar.isBanglaYearEn(dateBnYrOrCfg) ?
31
+ let bnYear = _a.isBanglaYear(dateBnYrOrCfg) ? (0, convert_1.banglaToDigit)(dateBnYrOrCfg)
32
+ : (0, primitives_1.isNumber)(dateBnYrOrCfg) && _a.isBanglaYearEn(dateBnYrOrCfg) ?
32
33
  dateBnYrOrCfg
33
34
  : year;
34
- let bnMonth = BanglaCalendar.isBanglaMonth(bnMonthOrCfg) ? (0, convert_1.banglaToDigit)(bnMonthOrCfg)
35
- : BanglaCalendar.isBanglaMonthEn(bnMonthOrCfg) ? bnMonthOrCfg
35
+ let bnMonth = _a.isBanglaMonth(bnMonthOrCfg) ? (0, convert_1.banglaToDigit)(bnMonthOrCfg)
36
+ : _a.isBanglaMonthEn(bnMonthOrCfg) ? bnMonthOrCfg
36
37
  : month;
37
- let bnDate = BanglaCalendar.isBanglaDate(bnDateOrCfg) ? (0, convert_1.banglaToDigit)(bnDateOrCfg)
38
- : BanglaCalendar.isBanglaDateEn(bnDateOrCfg) ? bnDateOrCfg
38
+ let bnDate = _a.isBanglaDate(bnDateOrCfg) ? (0, convert_1.banglaToDigit)(bnDateOrCfg)
39
+ : _a.isBanglaDateEn(bnDateOrCfg) ? bnDateOrCfg
39
40
  : monthDate;
40
- if (BanglaCalendar.isBanglaDateString(dateBnYrOrCfg)) {
41
+ if (_a.isBanglaDateString(dateBnYrOrCfg)) {
41
42
  const parts = dateBnYrOrCfg.replace(/['"]/g, '').split('-');
42
43
  bnYear = (0, convert_1.banglaToDigit)(parts[0]);
43
44
  bnMonth = (0, convert_1.banglaToDigit)(parts[1]);
44
45
  bnDate = (0, convert_1.banglaToDigit)(parts[2]);
45
46
  }
46
47
  const { gregYear } = this.#processGregYear(bnYear, bnMonth);
47
- const { bnMonthTable } = this.#getGregYearBnMonthTable(gregYear, bnYear);
48
+ const { bnMonthTable } = this.#getBnMonthTableLeap(gregYear, bnYear);
48
49
  const monthRange = bnMonthTable[bnMonth - 1];
49
50
  if (bnDate > monthRange) {
50
51
  bnDate -= monthRange;
@@ -73,16 +74,28 @@ class BanglaCalendar {
73
74
  this.weekDay = wd;
74
75
  this.isoWeekDay = wd === 0 ? 7 : wd;
75
76
  }
77
+ [Symbol.toPrimitive](hint) {
78
+ if (hint === 'number')
79
+ return this.valueOf();
80
+ return this.toJSON();
81
+ }
76
82
  get [Symbol.toStringTag]() {
77
83
  return this.toJSON();
78
84
  }
85
+ valueOf() {
86
+ return this.toDate().getTime();
87
+ }
88
+ toJSON() {
89
+ const { year, month, date } = this;
90
+ return `${(0, helpers_1._padShunno)(year.bn, 4)}-${(0, helpers_1._padShunno)(month.bn)}-${(0, helpers_1._padShunno)(date.bn)}`;
91
+ }
79
92
  isLeapYear() {
80
93
  const { gregYear } = this.#processGregYear();
81
- return this.#getGregYearBnMonthTable(gregYear).isBnLeapYear;
94
+ return this.#getBnMonthTableLeap(gregYear).isBnLeapYear;
82
95
  }
83
96
  toDate() {
84
97
  const { baseGregYear, gregYear } = this.#processGregYear();
85
- const { bnMonthTable } = this.#getGregYearBnMonthTable(gregYear);
98
+ const { bnMonthTable } = this.#getBnMonthTableLeap(gregYear);
86
99
  const epoch = Date.UTC(baseGregYear, 3, 13);
87
100
  let days = this.date.en;
88
101
  for (let i = 0; i < this.month.en - 1; i++) {
@@ -101,31 +114,71 @@ class BanglaCalendar {
101
114
  const DAY = constants_1.BN_DAYS[this.weekDay];
102
115
  return (locale === 'en' ? DAY.en : DAY.bn);
103
116
  }
117
+ addDays(days) {
118
+ const date = this.toDate();
119
+ return new _a(date.setDate(date.getDate() + days), {
120
+ variant: this.variant,
121
+ });
122
+ }
123
+ addWeeks(weeks) {
124
+ const date = this.toDate();
125
+ return new _a(date.setDate(date.getDate() + weeks * 7), {
126
+ variant: this.variant,
127
+ });
128
+ }
129
+ addMonths(months, overflow = true) {
130
+ if (overflow) {
131
+ const current = this.toDate();
132
+ return new _a(current.setMonth(current.getMonth() + months), {
133
+ variant: this.variant,
134
+ });
135
+ }
136
+ else {
137
+ const { variant, year, month, date } = this;
138
+ let targetMonth = month.en + months;
139
+ let targetYear = year.en;
140
+ while (targetMonth > 12) {
141
+ targetMonth -= 12;
142
+ targetYear += 1;
143
+ }
144
+ while (targetMonth < 1) {
145
+ targetMonth += 12;
146
+ targetYear -= 1;
147
+ }
148
+ return this.#getClampedBnCal(targetYear, targetMonth, date.en, variant);
149
+ }
150
+ }
151
+ addYears(years, overflow = true) {
152
+ const { variant, year, month, date } = this;
153
+ const targetYear = year.en + years;
154
+ if (overflow) {
155
+ return new _a(targetYear, month.en, date.en, { variant });
156
+ }
157
+ else {
158
+ return this.#getClampedBnCal(targetYear, month.en, date.en, variant);
159
+ }
160
+ }
104
161
  startOfMonth() {
105
162
  const { year, month, variant } = this;
106
- return new BanglaCalendar(year.en, month.en, 1, { variant });
163
+ return new _a(year.en, month.en, 1, { variant });
107
164
  }
108
165
  endOfMonth() {
109
166
  const { year, month, variant } = this;
110
- return new BanglaCalendar(year.en, month.en, this.daysInMonth(), { variant });
167
+ return new _a(year.en, month.en, this.daysInMonth(), { variant });
111
168
  }
112
169
  startOfYear() {
113
170
  const { year, variant } = this;
114
- return new BanglaCalendar(year.en, 1, 1, { variant });
171
+ return new _a(year.en, 1, 1, { variant });
115
172
  }
116
173
  endOfYear() {
117
174
  const { year, variant } = this;
118
- return new BanglaCalendar(year.en, 12, 30, { variant });
175
+ return new _a(year.en, 12, 30, { variant });
119
176
  }
120
177
  daysInMonth(month) {
121
178
  const { gregYear } = this.#processGregYear();
122
- const { bnMonthTable } = this.#getGregYearBnMonthTable(gregYear);
179
+ const { bnMonthTable } = this.#getBnMonthTableLeap(gregYear);
123
180
  return bnMonthTable[(month ?? this.month.en) - 1];
124
181
  }
125
- toJSON() {
126
- const { year, month, date } = this;
127
- return `${year.bn.padStart(4, '০')}-${month.bn.padStart(2, '০')}-${date.bn.padStart(2, '০')}`;
128
- }
129
182
  toString() {
130
183
  return this.#toString('bn');
131
184
  }
@@ -137,21 +190,21 @@ class BanglaCalendar {
137
190
  const seasonName = this.getSeasonName();
138
191
  const M_NAME = constants_1.BN_MONTHS[month.en - 1];
139
192
  const D_NAME = constants_1.BN_DAYS[weekDay];
140
- const paddedYear = year.bn.padStart(4, '০');
193
+ const paddedYear = (0, helpers_1._padShunno)(year.bn, 4);
141
194
  const dateComponents = {
142
195
  YYYY: paddedYear,
143
196
  YY: paddedYear.slice(-2),
144
197
  yyyy: paddedYear,
145
198
  yy: paddedYear.slice(-2),
146
199
  M: month.bn,
147
- MM: month.bn.padStart(2, '০'),
200
+ MM: (0, helpers_1._padShunno)(month.bn),
148
201
  mmm: M_NAME.short,
149
202
  mmmm: M_NAME.bn,
150
203
  d: D_NAME.short,
151
204
  dd: D_NAME.bn.replace('বার', ''),
152
205
  ddd: D_NAME.bn,
153
206
  D: date.bn,
154
- DD: date.bn.padStart(2, '০'),
207
+ DD: (0, helpers_1._padShunno)(date.bn),
155
208
  Do: date.bn,
156
209
  S: seasonName,
157
210
  SS: seasonName + 'কাল',
@@ -163,13 +216,19 @@ class BanglaCalendar {
163
216
  const gregYear = (bnMonth ?? this.month.en) > 10 ? baseGregYear + 1 : baseGregYear;
164
217
  return { baseGregYear, gregYear };
165
218
  }
166
- #getGregYearBnMonthTable(gregYear, bnYear) {
219
+ #getBnMonthTableLeap(gregYear, bnYear) {
167
220
  const isBnLeapYear = (0, helpers_1._isBnLeapYear)(bnYear ?? this.year.en, gregYear, this.variant);
168
221
  const bnMonthTable = isBnLeapYear ?
169
222
  constants_1.BN_MONTH_TABLES?.[this.variant].leap
170
223
  : constants_1.BN_MONTH_TABLES?.[this.variant].normal;
171
224
  return { bnMonthTable, isBnLeapYear };
172
225
  }
226
+ #getClampedBnCal(tyBn, tmBn, cdBn, variant) {
227
+ const { gregYear } = this.#processGregYear(tyBn, tmBn);
228
+ const { bnMonthTable } = this.#getBnMonthTableLeap(gregYear, tyBn);
229
+ const tdBn = Math.min(cdBn, bnMonthTable[tmBn - 1]);
230
+ return new _a(tyBn, tmBn, tdBn, { variant });
231
+ }
173
232
  #processVariants(v1, v2, v3, v4) {
174
233
  return (this.$hasVariantConfig(v1) ? v1.variant
175
234
  : this.$hasVariantConfig(v2) ? v2.variant
@@ -216,9 +275,9 @@ class BanglaCalendar {
216
275
  static isBanglaDateString(value) {
217
276
  if ((0, primitives_1.isNonEmptyString)(value) && value.includes('-')) {
218
277
  const [year, month, date] = value.replace(/['"]/g, '').split('-');
219
- return (BanglaCalendar.isBanglaYear(year) &&
220
- BanglaCalendar.isBanglaMonth(month) &&
221
- BanglaCalendar.isBanglaDate(date));
278
+ return (_a.isBanglaYear(year) &&
279
+ _a.isBanglaMonth(month) &&
280
+ _a.isBanglaDate(date));
222
281
  }
223
282
  return false;
224
283
  }
@@ -226,3 +285,4 @@ class BanglaCalendar {
226
285
  exports.BanglaCalendar = BanglaCalendar;
227
286
  exports.BnCalendar = BanglaCalendar;
228
287
  exports.Bongabdo = BanglaCalendar;
288
+ _a = BanglaCalendar;
@@ -14,6 +14,8 @@ exports._getBnYear = _getBnYear;
14
14
  exports._getUtcTs = _getUtcTs;
15
15
  exports._getElapsedDays = _getElapsedDays;
16
16
  exports._bnDaysMonthIdx = _bnDaysMonthIdx;
17
+ exports._padZero = _padZero;
18
+ exports._padShunno = _padShunno;
17
19
  const utilities_1 = require("../number/utilities");
18
20
  const constants_1 = require("./constants");
19
21
  const guards_1 = require("./guards");
@@ -43,32 +45,32 @@ function _formatDateCore(format, dateComponents) {
43
45
  return result;
44
46
  }
45
47
  function _formatDate(format, year, month, day, date, hours, minutes, seconds, milliseconds, offset) {
46
- const paddedYear = String(year).padStart(4, '0');
48
+ const paddedYear = _padZero(year, 4);
47
49
  const dateComponents = {
48
50
  YYYY: paddedYear,
49
51
  YY: paddedYear.slice(-2),
50
52
  yyyy: paddedYear,
51
53
  yy: paddedYear.slice(-2),
52
54
  M: String(month + 1),
53
- MM: String(month + 1).padStart(2, '0'),
55
+ MM: _padZero(month + 1),
54
56
  mmm: constants_1.MONTHS[month].slice(0, 3),
55
57
  mmmm: constants_1.MONTHS[month],
56
58
  d: constants_1.DAYS[day].slice(0, 2),
57
59
  dd: constants_1.DAYS[day].slice(0, 3),
58
60
  ddd: constants_1.DAYS[day],
59
61
  D: String(date),
60
- DD: String(date).padStart(2, '0'),
62
+ DD: _padZero(date),
61
63
  Do: (0, utilities_1.getOrdinal)(date),
62
64
  H: String(hours),
63
- HH: String(hours).padStart(2, '0'),
65
+ HH: _padZero(hours),
64
66
  h: String(hours % 12 || 12),
65
- hh: String(hours % 12 || 12).padStart(2, '0'),
67
+ hh: _padZero(hours % 12 || 12),
66
68
  m: String(minutes),
67
- mm: String(minutes).padStart(2, '0'),
69
+ mm: _padZero(minutes),
68
70
  s: String(seconds),
69
- ss: String(seconds).padStart(2, '0'),
71
+ ss: _padZero(seconds),
70
72
  ms: String(milliseconds),
71
- mss: String(milliseconds).padStart(3, '0'),
73
+ mss: _padZero(milliseconds, 3),
72
74
  a: hours < 12 ? 'am' : 'pm',
73
75
  A: hours < 12 ? 'AM' : 'PM',
74
76
  Z: offset,
@@ -142,3 +144,9 @@ function _bnDaysMonthIdx(date, variant) {
142
144
  }
143
145
  return { days, monthIdx };
144
146
  }
147
+ function _padZero(value, length = 2) {
148
+ return String(value).padStart(length, '0');
149
+ }
150
+ function _padShunno(str, length = 2) {
151
+ return str.padStart(length, '০');
152
+ }
@@ -6,16 +6,15 @@ const specials_1 = require("../guards/specials");
6
6
  const constants_1 = require("./constants");
7
7
  const guards_1 = require("./guards");
8
8
  function parseMSec(value, sec = false) {
9
- if ((0, specials_1.isNumericString)(value)) {
9
+ if ((0, primitives_1.isNumber)(value) || (0, specials_1.isNumericString)(value)) {
10
10
  return _parse(`${value}s`, sec);
11
11
  }
12
12
  else if ((0, guards_1.isTimeWithUnit)(value)) {
13
13
  return _parse(value, sec);
14
14
  }
15
- else if ((0, primitives_1.isNumber)(value)) {
16
- return _parse(`${value}s`, sec);
15
+ else {
16
+ return NaN;
17
17
  }
18
- return NaN;
19
18
  }
20
19
  function _parse(str, sec = false) {
21
20
  if (!(0, primitives_1.isNonEmptyString)(str) || str.length > 100) {
@@ -59,7 +59,7 @@ const banglaPlugin = ($Chronos) => {
59
59
  const { monthIdx } = $bnDaysMonthIdx($Date(this), opts?.variant);
60
60
  const M_NAME = constants_1.BN_MONTHS[monthIdx];
61
61
  const month = this.getBanglaMonth();
62
- const year = this.getBanglaYear().padStart(4, '০');
62
+ const year = (0, helpers_1._padShunno)(this.getBanglaYear(), 4);
63
63
  const date = this.getBanglaDay();
64
64
  const seasonName = this.getBanglaSeasonName();
65
65
  const offset = (0, convert_1.digitToBangla)(this.getTimeZoneOffset());
@@ -69,25 +69,25 @@ const banglaPlugin = ($Chronos) => {
69
69
  yyyy: year,
70
70
  yy: year.slice(-2),
71
71
  M: month,
72
- MM: month.padStart(2, '০'),
72
+ MM: (0, helpers_1._padShunno)(month),
73
73
  mmm: M_NAME.short,
74
74
  mmmm: M_NAME.bn,
75
75
  d: D_NAME.short,
76
76
  dd: D_NAME.bn.replace('বার', ''),
77
77
  ddd: D_NAME.bn,
78
78
  D: date,
79
- DD: date.padStart(2, '০'),
79
+ DD: (0, helpers_1._padShunno)(date),
80
80
  Do: date,
81
81
  H: (0, convert_1.digitToBangla)(hour),
82
- HH: (0, convert_1.digitToBangla)(hour).padStart(2, '০'),
82
+ HH: (0, helpers_1._padShunno)((0, convert_1.digitToBangla)(hour)),
83
83
  h: (0, convert_1.digitToBangla)(hour % 12 || 12),
84
- hh: (0, convert_1.digitToBangla)(hour % 12 || 12).padStart(2, '০'),
84
+ hh: (0, helpers_1._padShunno)((0, convert_1.digitToBangla)(hour % 12 || 12)),
85
85
  m: (0, convert_1.digitToBangla)(minute),
86
- mm: (0, convert_1.digitToBangla)(minute).padStart(2, '০'),
86
+ mm: (0, helpers_1._padShunno)((0, convert_1.digitToBangla)(minute)),
87
87
  s: (0, convert_1.digitToBangla)(second),
88
- ss: (0, convert_1.digitToBangla)(second).padStart(2, '০'),
88
+ ss: (0, helpers_1._padShunno)((0, convert_1.digitToBangla)(second)),
89
89
  ms: (0, convert_1.digitToBangla)(millisecond),
90
- mss: (0, convert_1.digitToBangla)(millisecond).padStart(3, '০'),
90
+ mss: (0, helpers_1._padShunno)((0, convert_1.digitToBangla)(millisecond), 3),
91
91
  a: hour < 12 ? 'পূর্বাহ্ণ' : 'অপরাহ্ণ',
92
92
  A: hour < 12 ? 'পূর্বাহ্ণ' : 'অপরাহ্ণ',
93
93
  Z: offset,
@@ -75,9 +75,9 @@ export declare class BanglaCalendar {
75
75
  */
76
76
  constructor(config?: BnCalendarConfig);
77
77
  /**
78
- * * Creates a `BanglaCalendar` instance from a **Bangla** or **Gregorian** date string.
78
+ * * Creates a `BanglaCalendar` instance from a **Gregorian** or **Bangla** date string.
79
79
  *
80
- * @param date - Bangla or Gregorian (should be parsable by {@link Date} ) date string
80
+ * @param date - Gregorian (should be parsable by {@link Date}) or Bangla date string
81
81
  * @param config - Calendar configuration options
82
82
  *
83
83
  * @remarks
@@ -174,7 +174,31 @@ export declare class BanglaCalendar {
174
174
  * const bnCal = new BanglaCalendar('১৪৩০', '১', '১'); // ১ বৈশাখ ১৪৩০
175
175
  */
176
176
  constructor(bnYear: BanglaYear, bnMonth: BanglaMonth, bnDate: BanglaDate, config?: BnCalendarConfig);
177
+ [Symbol.toPrimitive](hint: string): string | number;
177
178
  get [Symbol.toStringTag](): string;
179
+ /**
180
+ * @instance Get timestamp in milliseconds for the current date.
181
+ * @remarks
182
+ * - Converts the current Bangla date to a Gregorian {@link Date} using {@link toDate()}.
183
+ * - Returns the Unix timestamp (in milliseconds) of the converted date.
184
+ * - The time component is normalized to midnight UTC during the conversion process.
185
+ */
186
+ valueOf(): number;
187
+ /**
188
+ * @instance Returns a string representation of the Bangla date in ISO-like format (YYYY-MM-DD with Bangla digits).
189
+ *
190
+ * @returns Bangla date string in the format: "YYYY-MM-DD" (e.g., "১৪৩০-০১-০১")
191
+ *
192
+ * @example
193
+ * const bnCal = new BanglaCalendar('2023-04-14');
194
+ * console.log(bnCal.toJSON()); // "১৪৩০-০১-০১"
195
+ *
196
+ * @remarks
197
+ * - This method is automatically called by {@link JSON.stringify()} method
198
+ * - Output follows the pattern: `"বছর-মাস-দিন"` with zero-padded Bangla digits
199
+ * - Month and date are padded to 2 digits, year to 4 digits
200
+ */
201
+ toJSON(): string;
178
202
  /**
179
203
  * * Checks if the current Bangla year is a leap year.
180
204
  *
@@ -261,6 +285,133 @@ export declare class BanglaCalendar {
261
285
  * - English names are the Latin transliterations of the Bangla names with standard English weekday names.
262
286
  */
263
287
  getDayName<Locale extends $BnEn = 'bn'>(locale?: Locale): BanglaDayName<Locale>;
288
+ /**
289
+ * @instance Adds days to the current Bangla date.
290
+ *
291
+ * @param days - Number of days to add (can be negative to subtract days)
292
+ * @returns New `BanglaCalendar` instance with the adjusted date
293
+ *
294
+ * @example
295
+ * const bnCal = new BanglaCalendar('১৪৩০', '১', '১'); // ১ বৈশাখ ১৪৩০
296
+ *
297
+ * // Add days
298
+ * bnCal.addDays(7); // Returns: ৮ বৈশাখ ১৪৩০
299
+ *
300
+ * // Subtract days
301
+ * bnCal.addDays(-3); // Returns: ২৮ চৈত্র ১৪২৯
302
+ *
303
+ * // Add days crossing month boundary
304
+ * bnCal.addDays(35); // Returns: ৫ জ্যৈষ্ঠ ১৪৩০
305
+ *
306
+ * // Add days crossing year boundary
307
+ * const lateDate = new BanglaCalendar('১৪৩০', '১২', '২৫');
308
+ * lateDate.addDays(10); // Returns: ৫ বৈশাখ ১৪৩১
309
+ *
310
+ * @remarks
311
+ * - The resulting instance preserves the calendar variant of the original
312
+ * - Handles month and year transitions automatically
313
+ * - Accounts for varying month lengths and leap years
314
+ * - Time component remains at midnight UTC in the Gregorian conversion (using {@link BanglaCalendar.toDate()} method)
315
+ * - Negative values subtract days from the current date
316
+ */
317
+ addDays(days: number): BanglaCalendar;
318
+ /**
319
+ * @instance Adds weeks to the current Bangla date.
320
+ *
321
+ * @param weeks - Number of weeks to add (can be negative to subtract weeks)
322
+ * @returns New `BanglaCalendar` instance with the adjusted date
323
+ *
324
+ * @example
325
+ * const bnCal = new BanglaCalendar('১৪৩০', '১', '১'); // ১ বৈশাখ ১৪৩০
326
+ *
327
+ * // Add weeks
328
+ * bnCal.addWeeks(2); // Returns: ১৫ বৈশাখ ১৪৩০
329
+ *
330
+ * // Subtract weeks
331
+ * bnCal.addWeeks(-1); // Returns: ২৪ চৈত্র ১৪২৯
332
+ *
333
+ * // Add weeks crossing month boundary
334
+ * bnCal.addWeeks(5); // Returns: ৫ জ্যৈষ্ঠ ১৪৩০
335
+ *
336
+ * @remarks
337
+ * - Each week is treated as 7 days
338
+ * - The resulting instance preserves the calendar variant of the original
339
+ * - Handles month and year transitions automatically
340
+ * - Time component remains at midnight UTC in the Gregorian conversion (using {@link BanglaCalendar.toDate()} method)
341
+ * - Negative values subtract weeks from the current date
342
+ * - Useful for scheduling recurring weekly events
343
+ */
344
+ addWeeks(weeks: number): BanglaCalendar;
345
+ /**
346
+ * @instance Adds months to the current Bangla date.
347
+ *
348
+ * @param months - Number of months to add (can be negative to subtract months)
349
+ * @param overflow - If `true`, allows date overflow to next month when day doesn't exist;
350
+ * if `false`, clamps to last day of target month (default: `true`)
351
+ * @returns New `BanglaCalendar` instance with the adjusted date
352
+ *
353
+ * @example
354
+ * // Normal case: day exists in target month
355
+ * const normal = new BanglaCalendar('১৪৩০', '২', '১৫');
356
+ * normal.addMonths(1); // Returns: ১৫ আষাঢ় ১৪৩০
357
+ * normal.addMonths(1, false); // Returns: ১৫ আষাঢ় ১৪৩০ (same behavior for both)
358
+ *
359
+ * // Edge case: day does not exist in target month
360
+ * const edgeCase = new BanglaCalendar('১৪৩০', '৬', '৩১'); // ৩১ আশ্বিন ১৪৩০
361
+ *
362
+ * // With overflow (default): 31st doesn't exist in কার্তিক (30 days)
363
+ * edgeCase.addMonths(1); // Returns: ১ অগ্রহায়ণ ১৪৩০ (overflows to next month)
364
+ *
365
+ * // Without overflow: clamps to last day of target month
366
+ * edgeCase.addMonths(1, false); // Returns: ৩০ কার্তিক ১৪৩০ (clamped)
367
+ *
368
+ * // Subtract months
369
+ * edgeCase.addMonths(-1); // Returns: ১ আশ্বিন ১৪৩০
370
+ * edgeCase.addMonths(-1, false); // Returns: ৩১ ভাদ্র ১৪৩০
371
+ *
372
+ * @remarks
373
+ * - When `overflow=true` (default):
374
+ * Follows JavaScript {@link Date} behavior where invalid dates overflow to the next month (e.g., ৩১ আশ্বিন + 1 month → ১ অগ্রহায়ণ)
375
+ * - When `overflow=false`:
376
+ * Clamps to the last valid day of the target month (e.g., ৩১ আশ্বিন + 1 month → ৩০ কার্তিক)
377
+ * - The resulting instance preserves the calendar variant of the original
378
+ * - Handles year transitions automatically
379
+ * - Time component remains at midnight UTC in the Gregorian conversion (using {@link BanglaCalendar.toDate()} method)
380
+ * - Negative values subtract months from the current date
381
+ */
382
+ addMonths(months: number, overflow?: boolean): BanglaCalendar;
383
+ /**
384
+ * @instance Adds years to the current Bangla date.
385
+ *
386
+ * @param years - Number of years to add (can be negative to subtract years)
387
+ * @param overflow - If `true`, allows date overflow when day doesn't exist in target year;
388
+ * if `false`, clamps to last valid day of month (default: `true`)
389
+ * @returns New `BanglaCalendar` instance with the adjusted date
390
+ *
391
+ * @example
392
+ * const bnCal = new BanglaCalendar('১৪৩০', '১', '১৫'); // ১৫ বৈশাখ ১৪৩০
393
+ *
394
+ * // Add years
395
+ * bnCal.addYears(1); // Returns: ১৫ বৈশাখ ১৪৩১
396
+ *
397
+ * // Subtract years
398
+ * bnCal.addYears(-1); // Returns: ১৫ বৈশাখ ১৪২৯
399
+ *
400
+ * // Multiple years
401
+ * bnCal.addYears(5); // Returns: ১৫ বৈশাখ ১৪৩৫
402
+ *
403
+ * // Edge case: day adjustment for ফাল্গুন (accounting leap year)
404
+ * const leapDay = new BanglaCalendar('১৪৩১', '১১', '৩০'); // ১৪৩১ is a leap year
405
+ * leapDay.addYears(1, false); // Returns: ২৯ ফাল্গুন ১৪৩২ (non-leap years have 29 days in ফাল্গুন)
406
+ *
407
+ * @remarks
408
+ * - The resulting instance preserves the calendar variant of the original
409
+ * - Negative values subtract years from the current date
410
+ * - Year addition follows Bangla calendar years
411
+ * - Time component remains at midnight UTC in the Gregorian conversion (using {@link BanglaCalendar.toDate()} method)
412
+ * - The month and day generally remain the same unless affected by leap year rules
413
+ */
414
+ addYears(years: number, overflow?: boolean): BanglaCalendar;
264
415
  /**
265
416
  * @instance Gets a new `BanglaCalendar` instance representing the first day of the current month.
266
417
  *
@@ -272,8 +423,8 @@ export declare class BanglaCalendar {
272
423
  *
273
424
  * @remarks
274
425
  * - The resulting instance preserves the calendar variant of the original
275
- * - Time component is set to midnight UTC in the resulting Gregorian date
276
426
  * - Useful for date range calculations and month-based operations
427
+ * - Time component remains at midnight UTC in the Gregorian conversion (using {@link BanglaCalendar.toDate()} method)
277
428
  */
278
429
  startOfMonth(): BanglaCalendar;
279
430
  /**
@@ -288,7 +439,7 @@ export declare class BanglaCalendar {
288
439
  * @remarks
289
440
  * - The resulting instance preserves the calendar variant of the original
290
441
  * - Accounts for month length variations (29/30/31 days) including leap years
291
- * - Time component is set to midnight UTC in the resulting Gregorian date
442
+ * - Time component remains at midnight UTC in the Gregorian conversion (using {@link BanglaCalendar.toDate()} method)
292
443
  */
293
444
  endOfMonth(): BanglaCalendar;
294
445
  /**
@@ -303,7 +454,7 @@ export declare class BanglaCalendar {
303
454
  * @remarks
304
455
  * - The resulting instance preserves the calendar variant of the original
305
456
  * - Always returns the 1st day of the 1st month (বৈশাখ)
306
- * - Time component is set to midnight UTC in the resulting Gregorian date
457
+ * - Time component remains at midnight UTC in the Gregorian conversion (using {@link BanglaCalendar.toDate()} method)
307
458
  */
308
459
  startOfYear(): BanglaCalendar;
309
460
  /**
@@ -318,7 +469,7 @@ export declare class BanglaCalendar {
318
469
  * @remarks
319
470
  * - The resulting instance preserves the calendar variant of the original
320
471
  * - Always returns the 30th day of the 12th month (চৈত্র)
321
- * - Time component is set to midnight UTC in the resulting Gregorian date
472
+ * - Time component remains at midnight UTC in the Gregorian conversion (using {@link BanglaCalendar.toDate()} method)
322
473
  */
323
474
  endOfYear(): BanglaCalendar;
324
475
  /**
@@ -344,21 +495,6 @@ export declare class BanglaCalendar {
344
495
  * - In the 'revised-1966' variant, leap years occur when `bnYear % 4 === 2`
345
496
  */
346
497
  daysInMonth(month?: NumberRange<1, 12>): NumberRange<29, 31>;
347
- /**
348
- * @instance Returns a string representation of the Bangla date in ISO-like format (YYYY-MM-DD with Bangla digits).
349
- *
350
- * @returns Bangla date string in the format: "YYYY-MM-DD" (e.g., "১৪৩০-০১-০১")
351
- *
352
- * @example
353
- * const bnCal = new BanglaCalendar('2023-04-14');
354
- * console.log(bnCal.toJSON()); // "১৪৩০-০১-০১"
355
- *
356
- * @remarks
357
- * - This method is automatically called by {@link JSON.stringify()} method
358
- * - Output follows the pattern: `"বছর-মাস-দিন"` with zero-padded Bangla digits
359
- * - Month and date are padded to 2 digits, year to 4 digits
360
- */
361
- toJSON(): string;
362
498
  /**
363
499
  * @instance Returns a string representation of the Bangla date in Bengali format.
364
500
  *
@@ -369,7 +505,6 @@ export declare class BanglaCalendar {
369
505
  * console.log(bnCal.toString()); // "শুক্রবার, ১ বৈশাখ, ১৪৩০ [গ্রীষ্ম]"
370
506
  *
371
507
  * @remarks
372
- * - This method is automatically called by {@link String.prototype.toString()} method
373
508
  * - Equivalent to calling {@link toStringEn()} with 'bn' locale
374
509
  * - Format includes day name, date, month name, year, and season in brackets
375
510
  * - Uses Bengali digits and Bengali month/day names
@@ -1,11 +1,11 @@
1
1
  import type { Enumerate, NumberRange } from '../number/types';
2
2
  import type { Maybe } from '../types/index';
3
3
  import type { $BnEn, $GMTOffset, $TimeZoneIdentifier, BanglaSeasonName, BnCalendarVariant, TimeZoneNameNative } from './types';
4
- /** Core formatting logic shared by `formatDate` and `Chronos` class */
4
+ /** Core formatting logic shared by `formatDate` and `Chronos`, `BanglaCalendar` classes */
5
5
  export declare function _formatDateCore(format: string, dateComponents: Record<string, string>): string;
6
6
  /** Core formatting logic shared by `formatDate` and `Chronos` class */
7
7
  export declare function _formatDate(format: string, year: number, month: number, day: number, date: number, hours: number, minutes: number, seconds: number, milliseconds: number, offset: string): string;
8
- /** Normalize a time string with by adding offset at the end */
8
+ /** Normalize a time string by adding offset at the end */
9
9
  export declare function _normalizeOffset(timeStr: string): string;
10
10
  /** Converts milliseconds to seconds */
11
11
  export declare const _toSeconds: (ms: number) => number;
@@ -18,8 +18,11 @@ type $ResolvedTzName<T extends $TzNameType> = Maybe<T extends 'long' ? TimeZoneN
18
18
  export declare function _resolveNativeTzName<T extends $TzNameType>(tzId: $TzId, type: T, date?: Date): $ResolvedTzName<T>;
19
19
  /** Convert `GMT±HH:mm` string to `UTC±HH:mm` format*/
20
20
  export declare function _gmtToUtcOffset(gmt: Maybe<string>): Maybe<"UTC+00:15" | "UTC+00:30" | "UTC+00:45" | "UTC+00:00" | "UTC+01:15" | "UTC+01:30" | "UTC+01:45" | "UTC+01:00" | "UTC+02:15" | "UTC+02:30" | "UTC+02:45" | "UTC+02:00" | "UTC+03:15" | "UTC+03:30" | "UTC+03:45" | "UTC+03:00" | "UTC+04:15" | "UTC+04:30" | "UTC+04:45" | "UTC+04:00" | "UTC+05:15" | "UTC+05:30" | "UTC+05:45" | "UTC+05:00" | "UTC+06:15" | "UTC+06:30" | "UTC+06:45" | "UTC+06:00" | "UTC+07:15" | "UTC+07:30" | "UTC+07:45" | "UTC+07:00" | "UTC+08:15" | "UTC+08:30" | "UTC+08:45" | "UTC+08:00" | "UTC+09:15" | "UTC+09:30" | "UTC+09:45" | "UTC+09:00" | "UTC+10:15" | "UTC+10:30" | "UTC+10:45" | "UTC+10:00" | "UTC+14:15" | "UTC+14:30" | "UTC+14:45" | "UTC+14:00" | "UTC+11:15" | "UTC+11:30" | "UTC+11:45" | "UTC+11:00" | "UTC+12:15" | "UTC+12:30" | "UTC+12:45" | "UTC+12:00" | "UTC+13:15" | "UTC+13:30" | "UTC+13:45" | "UTC+13:00" | "UTC-00:15" | "UTC-00:30" | "UTC-00:45" | "UTC-00:00" | "UTC-01:15" | "UTC-01:30" | "UTC-01:45" | "UTC-01:00" | "UTC-02:15" | "UTC-02:30" | "UTC-02:45" | "UTC-02:00" | "UTC-03:15" | "UTC-03:30" | "UTC-03:45" | "UTC-03:00" | "UTC-04:15" | "UTC-04:30" | "UTC-04:45" | "UTC-04:00" | "UTC-05:15" | "UTC-05:30" | "UTC-05:45" | "UTC-05:00" | "UTC-06:15" | "UTC-06:30" | "UTC-06:45" | "UTC-06:00" | "UTC-07:15" | "UTC-07:30" | "UTC-07:45" | "UTC-07:00" | "UTC-08:15" | "UTC-08:30" | "UTC-08:45" | "UTC-08:00" | "UTC-09:15" | "UTC-09:30" | "UTC-09:45" | "UTC-09:00" | "UTC-10:15" | "UTC-10:30" | "UTC-10:45" | "UTC-10:00" | "UTC-14:15" | "UTC-14:30" | "UTC-14:45" | "UTC-14:00" | "UTC-11:15" | "UTC-11:30" | "UTC-11:45" | "UTC-11:00" | "UTC-12:15" | "UTC-12:30" | "UTC-12:45" | "UTC-12:00" | "UTC-13:15" | "UTC-13:30" | "UTC-13:45" | "UTC-13:00">;
21
+ /** Get Bangla season name by month index (`0-11`) */
21
22
  export declare function _getBnSeason<L extends $BnEn = 'bn'>(month: number, locale?: L | $BnEn): BanglaSeasonName<L>;
23
+ /** Check whether a Bangla year is leap by Gregorian and Bangla years and calendar variant */
22
24
  export declare function _isBnLeapYear(by: number, gy: number, v?: BnCalendarVariant): boolean;
25
+ /** Extract selective unit values from {@link Date} object */
23
26
  export declare function _extractDateUnits(date: Date): {
24
27
  gy: number;
25
28
  $gm: Enumerate<12>;
@@ -27,12 +30,31 @@ export declare function _extractDateUnits(date: Date): {
27
30
  gd: NumberRange<1, 31>;
28
31
  wd: Enumerate<7>;
29
32
  };
33
+ /** Get Gregorian base year from {@link Date} object for Bangla year */
30
34
  export declare function _getGregBaseYear(date: Date): number;
35
+ /** Get Bangla year from {@link Date} object */
31
36
  export declare function _getBnYear(date: Date): number;
37
+ /** Get timestamp in milliseconds between midnight, January 1, 1970 (UTC) and the specified {@link Date} object */
32
38
  export declare function _getUtcTs(date: Date): number;
39
+ /** Get number of days elapsed since midnight April 14, 1970 (UTC) for specific {@link Date} */
33
40
  export declare function _getElapsedDays(date: Date): number;
41
+ /** Get number of days elapsed since midnight April 14, 1970 (UTC) and month index for specific `Date` and Bangla calendar variant */
34
42
  export declare function _bnDaysMonthIdx(date: Date, variant?: BnCalendarVariant): {
35
43
  days: number;
36
44
  monthIdx: number;
37
45
  };
46
+ /**
47
+ * Convert number to string and pad at the start with zero (`'0'`)
48
+ * @param value Value to convert and pad with
49
+ * @param length Maximum length to pad, default is `2`
50
+ * @returns The padded string
51
+ */
52
+ export declare function _padZero(value: number, length?: number): string;
53
+ /**
54
+ * Pad at the start of a string with Bangla zero (`'০'`)
55
+ * @param str String to pad with
56
+ * @param length Maximum length to pad, default is `2`
57
+ * @returns The padded string
58
+ */
59
+ export declare function _padShunno(str: string, length?: number): string;
38
60
  export {};
@@ -1,9 +1,10 @@
1
+ var _a;
1
2
  import { isObjectWithKeys } from '../guards/non-primitives.js';
2
3
  import { isInteger, isNonEmptyString, isNumber } from '../guards/primitives.js';
3
4
  import { isDateString } from '../guards/specials.js';
4
5
  import { banglaToDigit, digitToBangla } from '../number/convert.js';
5
6
  import { BN_DAYS, BN_MONTH_TABLES, BN_MONTHS, BN_YEAR_OFFSET, MS_PER_DAY } from './constants.js';
6
- import { _bnDaysMonthIdx, _extractDateUnits, _formatDateCore, _getBnSeason, _getBnYear, _isBnLeapYear, } from './helpers.js';
7
+ import { _bnDaysMonthIdx, _extractDateUnits, _formatDateCore, _getBnSeason, _getBnYear, _isBnLeapYear, _padShunno, } from './helpers.js';
7
8
  export class BanglaCalendar {
8
9
  variant;
9
10
  year;
@@ -15,33 +16,33 @@ export class BanglaCalendar {
15
16
  constructor(dateBnYrOrCfg, bnMonthOrCfg, bnDateOrCfg, config) {
16
17
  this.variant = this.#processVariants(dateBnYrOrCfg, bnMonthOrCfg, bnDateOrCfg, config);
17
18
  let date = dateBnYrOrCfg instanceof Date ? dateBnYrOrCfg : (new Date((isDateString(dateBnYrOrCfg) &&
18
- !BanglaCalendar.isBanglaDateString(dateBnYrOrCfg)) ?
19
+ !_a.isBanglaDateString(dateBnYrOrCfg)) ?
19
20
  dateBnYrOrCfg
20
- : isNumber(dateBnYrOrCfg) && !BanglaCalendar.isBanglaYearEn(dateBnYrOrCfg) ?
21
+ : isNumber(dateBnYrOrCfg) && !_a.isBanglaYearEn(dateBnYrOrCfg) ?
21
22
  dateBnYrOrCfg
22
23
  : Date.now()));
23
24
  if (isNaN(date.getTime())) {
24
25
  date = new Date();
25
26
  }
26
27
  const { year, month, monthDate } = this.#processDate(date);
27
- let bnYear = BanglaCalendar.isBanglaYear(dateBnYrOrCfg) ? banglaToDigit(dateBnYrOrCfg)
28
- : isNumber(dateBnYrOrCfg) && BanglaCalendar.isBanglaYearEn(dateBnYrOrCfg) ?
28
+ let bnYear = _a.isBanglaYear(dateBnYrOrCfg) ? banglaToDigit(dateBnYrOrCfg)
29
+ : isNumber(dateBnYrOrCfg) && _a.isBanglaYearEn(dateBnYrOrCfg) ?
29
30
  dateBnYrOrCfg
30
31
  : year;
31
- let bnMonth = BanglaCalendar.isBanglaMonth(bnMonthOrCfg) ? banglaToDigit(bnMonthOrCfg)
32
- : BanglaCalendar.isBanglaMonthEn(bnMonthOrCfg) ? bnMonthOrCfg
32
+ let bnMonth = _a.isBanglaMonth(bnMonthOrCfg) ? banglaToDigit(bnMonthOrCfg)
33
+ : _a.isBanglaMonthEn(bnMonthOrCfg) ? bnMonthOrCfg
33
34
  : month;
34
- let bnDate = BanglaCalendar.isBanglaDate(bnDateOrCfg) ? banglaToDigit(bnDateOrCfg)
35
- : BanglaCalendar.isBanglaDateEn(bnDateOrCfg) ? bnDateOrCfg
35
+ let bnDate = _a.isBanglaDate(bnDateOrCfg) ? banglaToDigit(bnDateOrCfg)
36
+ : _a.isBanglaDateEn(bnDateOrCfg) ? bnDateOrCfg
36
37
  : monthDate;
37
- if (BanglaCalendar.isBanglaDateString(dateBnYrOrCfg)) {
38
+ if (_a.isBanglaDateString(dateBnYrOrCfg)) {
38
39
  const parts = dateBnYrOrCfg.replace(/['"]/g, '').split('-');
39
40
  bnYear = banglaToDigit(parts[0]);
40
41
  bnMonth = banglaToDigit(parts[1]);
41
42
  bnDate = banglaToDigit(parts[2]);
42
43
  }
43
44
  const { gregYear } = this.#processGregYear(bnYear, bnMonth);
44
- const { bnMonthTable } = this.#getGregYearBnMonthTable(gregYear, bnYear);
45
+ const { bnMonthTable } = this.#getBnMonthTableLeap(gregYear, bnYear);
45
46
  const monthRange = bnMonthTable[bnMonth - 1];
46
47
  if (bnDate > monthRange) {
47
48
  bnDate -= monthRange;
@@ -70,16 +71,28 @@ export class BanglaCalendar {
70
71
  this.weekDay = wd;
71
72
  this.isoWeekDay = wd === 0 ? 7 : wd;
72
73
  }
74
+ [Symbol.toPrimitive](hint) {
75
+ if (hint === 'number')
76
+ return this.valueOf();
77
+ return this.toJSON();
78
+ }
73
79
  get [Symbol.toStringTag]() {
74
80
  return this.toJSON();
75
81
  }
82
+ valueOf() {
83
+ return this.toDate().getTime();
84
+ }
85
+ toJSON() {
86
+ const { year, month, date } = this;
87
+ return `${_padShunno(year.bn, 4)}-${_padShunno(month.bn)}-${_padShunno(date.bn)}`;
88
+ }
76
89
  isLeapYear() {
77
90
  const { gregYear } = this.#processGregYear();
78
- return this.#getGregYearBnMonthTable(gregYear).isBnLeapYear;
91
+ return this.#getBnMonthTableLeap(gregYear).isBnLeapYear;
79
92
  }
80
93
  toDate() {
81
94
  const { baseGregYear, gregYear } = this.#processGregYear();
82
- const { bnMonthTable } = this.#getGregYearBnMonthTable(gregYear);
95
+ const { bnMonthTable } = this.#getBnMonthTableLeap(gregYear);
83
96
  const epoch = Date.UTC(baseGregYear, 3, 13);
84
97
  let days = this.date.en;
85
98
  for (let i = 0; i < this.month.en - 1; i++) {
@@ -98,31 +111,71 @@ export class BanglaCalendar {
98
111
  const DAY = BN_DAYS[this.weekDay];
99
112
  return (locale === 'en' ? DAY.en : DAY.bn);
100
113
  }
114
+ addDays(days) {
115
+ const date = this.toDate();
116
+ return new _a(date.setDate(date.getDate() + days), {
117
+ variant: this.variant,
118
+ });
119
+ }
120
+ addWeeks(weeks) {
121
+ const date = this.toDate();
122
+ return new _a(date.setDate(date.getDate() + weeks * 7), {
123
+ variant: this.variant,
124
+ });
125
+ }
126
+ addMonths(months, overflow = true) {
127
+ if (overflow) {
128
+ const current = this.toDate();
129
+ return new _a(current.setMonth(current.getMonth() + months), {
130
+ variant: this.variant,
131
+ });
132
+ }
133
+ else {
134
+ const { variant, year, month, date } = this;
135
+ let targetMonth = month.en + months;
136
+ let targetYear = year.en;
137
+ while (targetMonth > 12) {
138
+ targetMonth -= 12;
139
+ targetYear += 1;
140
+ }
141
+ while (targetMonth < 1) {
142
+ targetMonth += 12;
143
+ targetYear -= 1;
144
+ }
145
+ return this.#getClampedBnCal(targetYear, targetMonth, date.en, variant);
146
+ }
147
+ }
148
+ addYears(years, overflow = true) {
149
+ const { variant, year, month, date } = this;
150
+ const targetYear = year.en + years;
151
+ if (overflow) {
152
+ return new _a(targetYear, month.en, date.en, { variant });
153
+ }
154
+ else {
155
+ return this.#getClampedBnCal(targetYear, month.en, date.en, variant);
156
+ }
157
+ }
101
158
  startOfMonth() {
102
159
  const { year, month, variant } = this;
103
- return new BanglaCalendar(year.en, month.en, 1, { variant });
160
+ return new _a(year.en, month.en, 1, { variant });
104
161
  }
105
162
  endOfMonth() {
106
163
  const { year, month, variant } = this;
107
- return new BanglaCalendar(year.en, month.en, this.daysInMonth(), { variant });
164
+ return new _a(year.en, month.en, this.daysInMonth(), { variant });
108
165
  }
109
166
  startOfYear() {
110
167
  const { year, variant } = this;
111
- return new BanglaCalendar(year.en, 1, 1, { variant });
168
+ return new _a(year.en, 1, 1, { variant });
112
169
  }
113
170
  endOfYear() {
114
171
  const { year, variant } = this;
115
- return new BanglaCalendar(year.en, 12, 30, { variant });
172
+ return new _a(year.en, 12, 30, { variant });
116
173
  }
117
174
  daysInMonth(month) {
118
175
  const { gregYear } = this.#processGregYear();
119
- const { bnMonthTable } = this.#getGregYearBnMonthTable(gregYear);
176
+ const { bnMonthTable } = this.#getBnMonthTableLeap(gregYear);
120
177
  return bnMonthTable[(month ?? this.month.en) - 1];
121
178
  }
122
- toJSON() {
123
- const { year, month, date } = this;
124
- return `${year.bn.padStart(4, '০')}-${month.bn.padStart(2, '০')}-${date.bn.padStart(2, '০')}`;
125
- }
126
179
  toString() {
127
180
  return this.#toString('bn');
128
181
  }
@@ -134,21 +187,21 @@ export class BanglaCalendar {
134
187
  const seasonName = this.getSeasonName();
135
188
  const M_NAME = BN_MONTHS[month.en - 1];
136
189
  const D_NAME = BN_DAYS[weekDay];
137
- const paddedYear = year.bn.padStart(4, '০');
190
+ const paddedYear = _padShunno(year.bn, 4);
138
191
  const dateComponents = {
139
192
  YYYY: paddedYear,
140
193
  YY: paddedYear.slice(-2),
141
194
  yyyy: paddedYear,
142
195
  yy: paddedYear.slice(-2),
143
196
  M: month.bn,
144
- MM: month.bn.padStart(2, '০'),
197
+ MM: _padShunno(month.bn),
145
198
  mmm: M_NAME.short,
146
199
  mmmm: M_NAME.bn,
147
200
  d: D_NAME.short,
148
201
  dd: D_NAME.bn.replace('বার', ''),
149
202
  ddd: D_NAME.bn,
150
203
  D: date.bn,
151
- DD: date.bn.padStart(2, '০'),
204
+ DD: _padShunno(date.bn),
152
205
  Do: date.bn,
153
206
  S: seasonName,
154
207
  SS: seasonName + 'কাল',
@@ -160,13 +213,19 @@ export class BanglaCalendar {
160
213
  const gregYear = (bnMonth ?? this.month.en) > 10 ? baseGregYear + 1 : baseGregYear;
161
214
  return { baseGregYear, gregYear };
162
215
  }
163
- #getGregYearBnMonthTable(gregYear, bnYear) {
216
+ #getBnMonthTableLeap(gregYear, bnYear) {
164
217
  const isBnLeapYear = _isBnLeapYear(bnYear ?? this.year.en, gregYear, this.variant);
165
218
  const bnMonthTable = isBnLeapYear ?
166
219
  BN_MONTH_TABLES?.[this.variant].leap
167
220
  : BN_MONTH_TABLES?.[this.variant].normal;
168
221
  return { bnMonthTable, isBnLeapYear };
169
222
  }
223
+ #getClampedBnCal(tyBn, tmBn, cdBn, variant) {
224
+ const { gregYear } = this.#processGregYear(tyBn, tmBn);
225
+ const { bnMonthTable } = this.#getBnMonthTableLeap(gregYear, tyBn);
226
+ const tdBn = Math.min(cdBn, bnMonthTable[tmBn - 1]);
227
+ return new _a(tyBn, tmBn, tdBn, { variant });
228
+ }
170
229
  #processVariants(v1, v2, v3, v4) {
171
230
  return (this.$hasVariantConfig(v1) ? v1.variant
172
231
  : this.$hasVariantConfig(v2) ? v2.variant
@@ -213,11 +272,12 @@ export class BanglaCalendar {
213
272
  static isBanglaDateString(value) {
214
273
  if (isNonEmptyString(value) && value.includes('-')) {
215
274
  const [year, month, date] = value.replace(/['"]/g, '').split('-');
216
- return (BanglaCalendar.isBanglaYear(year) &&
217
- BanglaCalendar.isBanglaMonth(month) &&
218
- BanglaCalendar.isBanglaDate(date));
275
+ return (_a.isBanglaYear(year) &&
276
+ _a.isBanglaMonth(month) &&
277
+ _a.isBanglaDate(date));
219
278
  }
220
279
  return false;
221
280
  }
222
281
  }
282
+ _a = BanglaCalendar;
223
283
  export { BanglaCalendar as BnCalendar, BanglaCalendar as Bongabdo };
@@ -27,32 +27,32 @@ export function _formatDateCore(format, dateComponents) {
27
27
  return result;
28
28
  }
29
29
  export function _formatDate(format, year, month, day, date, hours, minutes, seconds, milliseconds, offset) {
30
- const paddedYear = String(year).padStart(4, '0');
30
+ const paddedYear = _padZero(year, 4);
31
31
  const dateComponents = {
32
32
  YYYY: paddedYear,
33
33
  YY: paddedYear.slice(-2),
34
34
  yyyy: paddedYear,
35
35
  yy: paddedYear.slice(-2),
36
36
  M: String(month + 1),
37
- MM: String(month + 1).padStart(2, '0'),
37
+ MM: _padZero(month + 1),
38
38
  mmm: MONTHS[month].slice(0, 3),
39
39
  mmmm: MONTHS[month],
40
40
  d: DAYS[day].slice(0, 2),
41
41
  dd: DAYS[day].slice(0, 3),
42
42
  ddd: DAYS[day],
43
43
  D: String(date),
44
- DD: String(date).padStart(2, '0'),
44
+ DD: _padZero(date),
45
45
  Do: getOrdinal(date),
46
46
  H: String(hours),
47
- HH: String(hours).padStart(2, '0'),
47
+ HH: _padZero(hours),
48
48
  h: String(hours % 12 || 12),
49
- hh: String(hours % 12 || 12).padStart(2, '0'),
49
+ hh: _padZero(hours % 12 || 12),
50
50
  m: String(minutes),
51
- mm: String(minutes).padStart(2, '0'),
51
+ mm: _padZero(minutes),
52
52
  s: String(seconds),
53
- ss: String(seconds).padStart(2, '0'),
53
+ ss: _padZero(seconds),
54
54
  ms: String(milliseconds),
55
- mss: String(milliseconds).padStart(3, '0'),
55
+ mss: _padZero(milliseconds, 3),
56
56
  a: hours < 12 ? 'am' : 'pm',
57
57
  A: hours < 12 ? 'AM' : 'PM',
58
58
  Z: offset,
@@ -124,3 +124,9 @@ export function _bnDaysMonthIdx(date, variant) {
124
124
  }
125
125
  return { days, monthIdx };
126
126
  }
127
+ export function _padZero(value, length = 2) {
128
+ return String(value).padStart(length, '0');
129
+ }
130
+ export function _padShunno(str, length = 2) {
131
+ return str.padStart(length, '০');
132
+ }
@@ -3,16 +3,15 @@ import { isNumericString } from '../guards/specials.js';
3
3
  import { MS_MAP } from './constants.js';
4
4
  import { isTimeWithUnit } from './guards.js';
5
5
  export function parseMSec(value, sec = false) {
6
- if (isNumericString(value)) {
6
+ if (isNumber(value) || isNumericString(value)) {
7
7
  return _parse(`${value}s`, sec);
8
8
  }
9
9
  else if (isTimeWithUnit(value)) {
10
10
  return _parse(value, sec);
11
11
  }
12
- else if (isNumber(value)) {
13
- return _parse(`${value}s`, sec);
12
+ else {
13
+ return NaN;
14
14
  }
15
- return NaN;
16
15
  }
17
16
  function _parse(str, sec = false) {
18
17
  if (!isNonEmptyString(str) || str.length > 100) {
@@ -1,6 +1,6 @@
1
1
  import { digitToBangla } from '../../number/convert.js';
2
2
  import { BN_DAYS, BN_MONTHS, INTERNALS } from '../constants.js';
3
- import { _bnDaysMonthIdx, _formatDateCore, _getBnSeason, _getBnYear, _isBnLeapYear, } from '../helpers.js';
3
+ import { _bnDaysMonthIdx, _formatDateCore, _getBnSeason, _getBnYear, _isBnLeapYear, _padShunno, } from '../helpers.js';
4
4
  export const banglaPlugin = ($Chronos) => {
5
5
  const { internalDate: $Date } = $Chronos[INTERNALS];
6
6
  const DEFAULT_CONFIG = new Map();
@@ -56,7 +56,7 @@ export const banglaPlugin = ($Chronos) => {
56
56
  const { monthIdx } = $bnDaysMonthIdx($Date(this), opts?.variant);
57
57
  const M_NAME = BN_MONTHS[monthIdx];
58
58
  const month = this.getBanglaMonth();
59
- const year = this.getBanglaYear().padStart(4, '০');
59
+ const year = _padShunno(this.getBanglaYear(), 4);
60
60
  const date = this.getBanglaDay();
61
61
  const seasonName = this.getBanglaSeasonName();
62
62
  const offset = digitToBangla(this.getTimeZoneOffset());
@@ -66,25 +66,25 @@ export const banglaPlugin = ($Chronos) => {
66
66
  yyyy: year,
67
67
  yy: year.slice(-2),
68
68
  M: month,
69
- MM: month.padStart(2, '০'),
69
+ MM: _padShunno(month),
70
70
  mmm: M_NAME.short,
71
71
  mmmm: M_NAME.bn,
72
72
  d: D_NAME.short,
73
73
  dd: D_NAME.bn.replace('বার', ''),
74
74
  ddd: D_NAME.bn,
75
75
  D: date,
76
- DD: date.padStart(2, '০'),
76
+ DD: _padShunno(date),
77
77
  Do: date,
78
78
  H: digitToBangla(hour),
79
- HH: digitToBangla(hour).padStart(2, '০'),
79
+ HH: _padShunno(digitToBangla(hour)),
80
80
  h: digitToBangla(hour % 12 || 12),
81
- hh: digitToBangla(hour % 12 || 12).padStart(2, '০'),
81
+ hh: _padShunno(digitToBangla(hour % 12 || 12)),
82
82
  m: digitToBangla(minute),
83
- mm: digitToBangla(minute).padStart(2, '০'),
83
+ mm: _padShunno(digitToBangla(minute)),
84
84
  s: digitToBangla(second),
85
- ss: digitToBangla(second).padStart(2, '০'),
85
+ ss: _padShunno(digitToBangla(second)),
86
86
  ms: digitToBangla(millisecond),
87
- mss: digitToBangla(millisecond).padStart(3, '০'),
87
+ mss: _padShunno(digitToBangla(millisecond), 3),
88
88
  a: hour < 12 ? 'পূর্বাহ্ণ' : 'অপরাহ্ণ',
89
89
  A: hour < 12 ? 'পূর্বাহ্ণ' : 'অপরাহ্ণ',
90
90
  Z: offset,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "nhb-toolbox",
3
- "version": "4.28.51",
3
+ "version": "4.28.53",
4
4
  "description": "A versatile collection of smart, efficient, and reusable utility functions, classes and types for everyday development needs.",
5
5
  "main": "dist/cjs/index.js",
6
6
  "module": "dist/esm/index.js",
@@ -47,8 +47,8 @@
47
47
  "@eslint/js": "^9.39.2",
48
48
  "@types/jest": "^30.0.0",
49
49
  "@types/node": "^25.0.3",
50
- "@typescript-eslint/eslint-plugin": "^8.50.1",
51
- "@typescript-eslint/parser": "^8.50.1",
50
+ "@typescript-eslint/eslint-plugin": "^8.51.0",
51
+ "@typescript-eslint/parser": "^8.51.0",
52
52
  "eslint": "^9.39.2",
53
53
  "eslint-config-prettier": "^10.1.8",
54
54
  "eslint-plugin-prettier": "^5.5.4",
@@ -60,7 +60,7 @@
60
60
  "prettier": "^3.7.4",
61
61
  "ts-jest": "^29.4.6",
62
62
  "typescript": "^5.9.3",
63
- "typescript-eslint": "^8.50.1"
63
+ "typescript-eslint": "^8.51.0"
64
64
  },
65
65
  "keywords": [
66
66
  "toolbox",