@lichta/core 2.0.1 → 2.2.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 +134 -13
- package/dist/index.d.mts +468 -89
- package/dist/index.d.ts +468 -89
- package/dist/index.js +583 -99
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +551 -98
- package/dist/index.mjs.map +1 -1
- package/package.json +2 -1
- package/styles/calendar-base.css +21 -6
- package/styles/calendar-glass.css +2 -12
- package/styles/datepicker-base.css +223 -0
- package/styles/datepicker-glass.css +27 -0
package/dist/index.js
CHANGED
|
@@ -15,7 +15,7 @@ var __copyProps = (to, from, except, desc) => {
|
|
|
15
15
|
}
|
|
16
16
|
return to;
|
|
17
17
|
};
|
|
18
|
-
var __toCommonJS = (
|
|
18
|
+
var __toCommonJS = (mod2) => __copyProps(__defProp({}, "__esModule", { value: true }), mod2);
|
|
19
19
|
|
|
20
20
|
// src/index.ts
|
|
21
21
|
var index_exports = {};
|
|
@@ -23,14 +23,45 @@ __export(index_exports, {
|
|
|
23
23
|
LichTa: () => LichTa,
|
|
24
24
|
formatLunarDate: () => formatLunarDate,
|
|
25
25
|
formatTraditional: () => formatTraditional,
|
|
26
|
+
getAuspiciousHourIndices: () => getAuspiciousHourIndices,
|
|
26
27
|
getAuspiciousHours: () => getAuspiciousHours,
|
|
28
|
+
getCalendarGrid: () => getCalendarGrid,
|
|
27
29
|
getDayCanChi: () => getDayCanChi,
|
|
30
|
+
getDayElement: () => getDayElement,
|
|
31
|
+
getDayElementIndex: () => getDayElementIndex,
|
|
28
32
|
getDayName: () => getDayName,
|
|
33
|
+
getElementName: () => getElementName,
|
|
34
|
+
getElementRelation: () => getElementRelation,
|
|
35
|
+
getElementRelationIndex: () => getElementRelationIndex,
|
|
36
|
+
getHaiBranchIndex: () => getHaiBranchIndex,
|
|
29
37
|
getHourCanChi: () => getHourCanChi,
|
|
38
|
+
getHourElement: () => getHourElement,
|
|
39
|
+
getHourElementIndex: () => getHourElementIndex,
|
|
40
|
+
getISOWeekNumber: () => getISOWeekNumber,
|
|
41
|
+
getInauspiciousHourIndices: () => getInauspiciousHourIndices,
|
|
42
|
+
getInauspiciousHours: () => getInauspiciousHours,
|
|
30
43
|
getMonthCanChi: () => getMonthCanChi,
|
|
44
|
+
getMonthElement: () => getMonthElement,
|
|
45
|
+
getMonthElementIndex: () => getMonthElementIndex,
|
|
31
46
|
getMonthName: () => getMonthName,
|
|
47
|
+
getSolarTerm: () => getSolarTerm,
|
|
48
|
+
getSolarTermName: () => getSolarTermName,
|
|
49
|
+
getSolarTermsInYear: () => getSolarTermsInYear,
|
|
50
|
+
getTruc: () => getTruc,
|
|
51
|
+
getTrucIndex: () => getTrucIndex,
|
|
52
|
+
getTrucName: () => getTrucName,
|
|
53
|
+
getTrucQuality: () => getTrucQuality,
|
|
54
|
+
getTrucQualityIndex: () => getTrucQualityIndex,
|
|
55
|
+
getTuHanhXungGroupIndex: () => getTuHanhXungGroupIndex,
|
|
56
|
+
getTuHanhXungGroupMembers: () => getTuHanhXungGroupMembers,
|
|
57
|
+
getWeekDayLabels: () => getWeekDayLabels,
|
|
58
|
+
getXungBranchIndex: () => getXungBranchIndex,
|
|
32
59
|
getYearDetails: () => getYearDetails,
|
|
33
60
|
getZodiacAnimal: () => getZodiacAnimal,
|
|
61
|
+
getZodiacConflicts: () => getZodiacConflicts,
|
|
62
|
+
isHai: () => isHai,
|
|
63
|
+
isTuHanhXung: () => isTuHanhXung,
|
|
64
|
+
isXung: () => isXung,
|
|
34
65
|
jdFromDate: () => jdFromDate,
|
|
35
66
|
jdToDate: () => jdToDate,
|
|
36
67
|
t: () => t
|
|
@@ -50,9 +81,6 @@ var HEAVENLY_STEMS = [
|
|
|
50
81
|
"Nh\xE2m",
|
|
51
82
|
"Qu\xFD"
|
|
52
83
|
];
|
|
53
|
-
function getStemWeight(index) {
|
|
54
|
-
return Math.floor(index / 2) + 1;
|
|
55
|
-
}
|
|
56
84
|
|
|
57
85
|
// src/constants/earthly-branches.ts
|
|
58
86
|
var EARTHLY_BRANCHES = [
|
|
@@ -69,12 +97,8 @@ var EARTHLY_BRANCHES = [
|
|
|
69
97
|
"Tu\u1EA5t",
|
|
70
98
|
"H\u1EE3i"
|
|
71
99
|
];
|
|
72
|
-
function getBranchWeight(index) {
|
|
73
|
-
const normalizedIndex = index % 6;
|
|
74
|
-
return Math.floor(normalizedIndex / 2);
|
|
75
|
-
}
|
|
76
100
|
|
|
77
|
-
// src/core/
|
|
101
|
+
// src/core/astronomical.ts
|
|
78
102
|
var PI = Math.PI;
|
|
79
103
|
function INT(d) {
|
|
80
104
|
return Math.floor(d);
|
|
@@ -130,7 +154,7 @@ function NewMoon(k) {
|
|
|
130
154
|
function getNewMoonDay(k, timeZone) {
|
|
131
155
|
return INT(NewMoon(k) + 0.5 + timeZone / 24);
|
|
132
156
|
}
|
|
133
|
-
function
|
|
157
|
+
function sunLongitudeDegrees(jdn, timeZone) {
|
|
134
158
|
const T = (jdn - 24515455e-1 - timeZone / 24) / 36525;
|
|
135
159
|
const T2 = T * T;
|
|
136
160
|
const dr = PI / 180;
|
|
@@ -140,11 +164,22 @@ function getSunLongitude(jdn, timeZone) {
|
|
|
140
164
|
DL = DL + (0.019993 - 101e-6 * T) * Math.sin(dr * 2 * M) + 29e-5 * Math.sin(dr * 3 * M);
|
|
141
165
|
let L = L0 + DL;
|
|
142
166
|
L = L - 360 * INT(L / 360);
|
|
143
|
-
return
|
|
167
|
+
return L;
|
|
168
|
+
}
|
|
169
|
+
function getSunLongitude(jdn, timeZone) {
|
|
170
|
+
return INT(sunLongitudeDegrees(jdn, timeZone) / 30);
|
|
171
|
+
}
|
|
172
|
+
function getSolarTermIndex(jdn, timeZone) {
|
|
173
|
+
return INT(sunLongitudeDegrees(jdn, timeZone) / 15);
|
|
174
|
+
}
|
|
175
|
+
|
|
176
|
+
// src/core/calendar-engine.ts
|
|
177
|
+
function INT2(d) {
|
|
178
|
+
return Math.floor(d);
|
|
144
179
|
}
|
|
145
180
|
function getLunarMonth11(yy, timeZone) {
|
|
146
181
|
const off = jdFromDate(31, 12, yy) - 2415021076998695e-9;
|
|
147
|
-
const k =
|
|
182
|
+
const k = INT2(off / 29.530588853);
|
|
148
183
|
let nm = getNewMoonDay(k, timeZone);
|
|
149
184
|
const sunLong = getSunLongitude(nm, timeZone);
|
|
150
185
|
if (sunLong >= 9) {
|
|
@@ -153,7 +188,7 @@ function getLunarMonth11(yy, timeZone) {
|
|
|
153
188
|
return nm;
|
|
154
189
|
}
|
|
155
190
|
function getLeapMonthOffset(a11, timeZone) {
|
|
156
|
-
const k =
|
|
191
|
+
const k = INT2((a11 - 2415021076998695e-9) / 29.530588853 + 0.5);
|
|
157
192
|
let last;
|
|
158
193
|
let i = 1;
|
|
159
194
|
let arc = getSunLongitude(getNewMoonDay(k + i, timeZone), timeZone);
|
|
@@ -217,7 +252,7 @@ var LichTa = class {
|
|
|
217
252
|
throw new RangeError(`Lichta: Day must be between 1 and 31, got ${day}`);
|
|
218
253
|
}
|
|
219
254
|
const dayNumber = jdFromDate(day, month, year);
|
|
220
|
-
const k =
|
|
255
|
+
const k = INT2((dayNumber - 2415021076998695e-9) / 29.530588853);
|
|
221
256
|
let monthStart = getNewMoonDay(k + 1, timeZone);
|
|
222
257
|
if (monthStart > dayNumber) {
|
|
223
258
|
monthStart = getNewMoonDay(k, timeZone);
|
|
@@ -233,7 +268,7 @@ var LichTa = class {
|
|
|
233
268
|
b11 = getLunarMonth11(year + 1, timeZone);
|
|
234
269
|
}
|
|
235
270
|
const lunarDay = dayNumber - monthStart + 1;
|
|
236
|
-
const diff =
|
|
271
|
+
const diff = INT2((monthStart - a11) / 29);
|
|
237
272
|
let lunarLeap = false;
|
|
238
273
|
let lunarMonth = diff + 11;
|
|
239
274
|
if (b11 - a11 > 365) {
|
|
@@ -294,7 +329,7 @@ var LichTa = class {
|
|
|
294
329
|
a11 = getLunarMonth11(lunarYear, timeZone);
|
|
295
330
|
b11 = getLunarMonth11(lunarYear + 1, timeZone);
|
|
296
331
|
}
|
|
297
|
-
const k =
|
|
332
|
+
const k = INT2(0.5 + (a11 - 2415021076998695e-9) / 29.530588853);
|
|
298
333
|
let off = lunarMonth - 11;
|
|
299
334
|
if (off < 0) {
|
|
300
335
|
off += 12;
|
|
@@ -318,45 +353,445 @@ var LichTa = class {
|
|
|
318
353
|
}
|
|
319
354
|
};
|
|
320
355
|
|
|
321
|
-
// src/constants/
|
|
322
|
-
var
|
|
356
|
+
// src/constants/i18n.ts
|
|
357
|
+
var translations = {
|
|
358
|
+
vi: {
|
|
359
|
+
heavenlyStems: ["Gi\xE1p", "\u1EA4t", "B\xEDnh", "\u0110inh", "M\u1EADu", "K\u1EF7", "Canh", "T\xE2n", "Nh\xE2m", "Qu\xFD"],
|
|
360
|
+
earthlyBranches: ["T\xFD", "S\u1EEDu", "D\u1EA7n", "M\xE3o", "Th\xECn", "T\u1EF5", "Ng\u1ECD", "M\xF9i", "Th\xE2n", "D\u1EADu", "Tu\u1EA5t", "H\u1EE3i"],
|
|
361
|
+
fiveElements: ["Kim", "M\u1ED9c", "Th\u1EE7y", "H\u1ECFa", "Th\u1ED5"],
|
|
362
|
+
zodiacAnimals: ["Chu\u1ED9t", "Tr\xE2u", "C\u1ECDp", "Th\u1ECF", "R\u1ED3ng", "R\u1EAFn", "Ng\u1EF1a", "D\xEA", "Kh\u1EC9", "G\xE0", "Ch\xF3", "Heo"],
|
|
363
|
+
// @deprecated Ngữ nghĩa không nhất quán giữa các locale (xem lunarMonthNames/solarMonthNames).
|
|
364
|
+
monthNames: ["Gi\xEAng", "Hai", "Ba", "T\u01B0", "N\u0103m", "S\xE1u", "B\u1EA3y", "T\xE1m", "Ch\xEDn", "M\u01B0\u1EDDi", "M\u1ED9t", "Ch\u1EA1p"],
|
|
365
|
+
lunarMonthNames: ["Gi\xEAng", "Hai", "Ba", "T\u01B0", "N\u0103m", "S\xE1u", "B\u1EA3y", "T\xE1m", "Ch\xEDn", "M\u01B0\u1EDDi", "M\u1ED9t", "Ch\u1EA1p"],
|
|
366
|
+
solarMonthNames: ["Th\xE1ng 1", "Th\xE1ng 2", "Th\xE1ng 3", "Th\xE1ng 4", "Th\xE1ng 5", "Th\xE1ng 6", "Th\xE1ng 7", "Th\xE1ng 8", "Th\xE1ng 9", "Th\xE1ng 10", "Th\xE1ng 11", "Th\xE1ng 12"],
|
|
367
|
+
weekDays: ["CN", "T2", "T3", "T4", "T5", "T6", "T7"],
|
|
368
|
+
leapLabel: "Nhu\u1EADn",
|
|
369
|
+
yearLabel: "N\u0103m",
|
|
370
|
+
monthLabel: "Th\xE1ng",
|
|
371
|
+
destiny: "M\u1EC7nh",
|
|
372
|
+
// Thứ tự bắt đầu từ Xuân Phân (kinh độ Mặt Trời 0°), xem getSolarTermIndex trong lunar.ts
|
|
373
|
+
solarTermNames: [
|
|
374
|
+
"Xu\xE2n Ph\xE2n",
|
|
375
|
+
"Thanh Minh",
|
|
376
|
+
"C\u1ED1c V\u0169",
|
|
377
|
+
"L\u1EADp H\u1EA1",
|
|
378
|
+
"Ti\u1EC3u M\xE3n",
|
|
379
|
+
"Mang Ch\u1EE7ng",
|
|
380
|
+
"H\u1EA1 Ch\xED",
|
|
381
|
+
"Ti\u1EC3u Th\u1EED",
|
|
382
|
+
"\u0110\u1EA1i Th\u1EED",
|
|
383
|
+
"L\u1EADp Thu",
|
|
384
|
+
"X\u1EED Th\u1EED",
|
|
385
|
+
"B\u1EA1ch L\u1ED9",
|
|
386
|
+
"Thu Ph\xE2n",
|
|
387
|
+
"H\xE0n L\u1ED9",
|
|
388
|
+
"S\u01B0\u01A1ng Gi\xE1ng",
|
|
389
|
+
"L\u1EADp \u0110\xF4ng",
|
|
390
|
+
"Ti\u1EC3u Tuy\u1EBFt",
|
|
391
|
+
"\u0110\u1EA1i Tuy\u1EBFt",
|
|
392
|
+
"\u0110\xF4ng Ch\xED",
|
|
393
|
+
"Ti\u1EC3u H\xE0n",
|
|
394
|
+
"\u0110\u1EA1i H\xE0n",
|
|
395
|
+
"L\u1EADp Xu\xE2n",
|
|
396
|
+
"V\u0169 Th\u1EE7y",
|
|
397
|
+
"Kinh Tr\u1EADp"
|
|
398
|
+
],
|
|
399
|
+
// Thứ tự bắt đầu từ Kiến (0), xem getTrucIndex trong feng-shui.ts
|
|
400
|
+
trucNames: ["Ki\u1EBFn", "Tr\u1EEB", "M\xE3n", "B\xECnh", "\u0110\u1ECBnh", "Ch\u1EA5p", "Ph\xE1", "Nguy", "Th\xE0nh", "Thu", "Khai", "B\u1EBF"],
|
|
401
|
+
// Thứ tự: sinh, được sinh, khắc, bị khắc, hòa — xem getElementRelationIndex trong feng-shui.ts
|
|
402
|
+
elementRelationNames: ["T\u01B0\u01A1ng sinh", "\u0110\u01B0\u1EE3c sinh", "T\u01B0\u01A1ng kh\u1EAFc", "B\u1ECB kh\u1EAFc", "T\u01B0\u01A1ng h\xF2a"],
|
|
403
|
+
// Thứ tự: xấu, trung bình, tốt — xem getTrucQualityIndex trong feng-shui.ts
|
|
404
|
+
trucQualityNames: ["X\u1EA5u", "Trung b\xECnh", "T\u1ED1t"]
|
|
405
|
+
},
|
|
406
|
+
en: {
|
|
407
|
+
heavenlyStems: ["Gi\xE1p", "\u1EA4t", "B\xEDnh", "\u0110inh", "M\u1EADu", "K\u1EF7", "Canh", "T\xE2n", "Nh\xE2m", "Qu\xFD"],
|
|
408
|
+
earthlyBranches: ["T\xFD", "S\u1EEDu", "D\u1EA7n", "M\xE3o", "Th\xECn", "T\u1EF5", "Ng\u1ECD", "M\xF9i", "Th\xE2n", "D\u1EADu", "Tu\u1EA5t", "H\u1EE3i"],
|
|
409
|
+
fiveElements: ["Metal", "Wood", "Water", "Fire", "Earth"],
|
|
410
|
+
zodiacAnimals: ["Rat", "Ox", "Tiger", "Rabbit", "Dragon", "Snake", "Horse", "Goat", "Monkey", "Rooster", "Dog", "Pig"],
|
|
411
|
+
// @deprecated Ngữ nghĩa không nhất quán giữa các locale (xem lunarMonthNames/solarMonthNames).
|
|
412
|
+
monthNames: ["January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"],
|
|
413
|
+
lunarMonthNames: ["Month 1", "Month 2", "Month 3", "Month 4", "Month 5", "Month 6", "Month 7", "Month 8", "Month 9", "Month 10", "Month 11", "Month 12"],
|
|
414
|
+
solarMonthNames: ["January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"],
|
|
415
|
+
weekDays: ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"],
|
|
416
|
+
leapLabel: "Leap",
|
|
417
|
+
yearLabel: "Year",
|
|
418
|
+
monthLabel: "Month",
|
|
419
|
+
destiny: "Destiny",
|
|
420
|
+
solarTermNames: [
|
|
421
|
+
"Spring Equinox",
|
|
422
|
+
"Clear and Bright",
|
|
423
|
+
"Grain Rain",
|
|
424
|
+
"Start of Summer",
|
|
425
|
+
"Grain Full",
|
|
426
|
+
"Grain in Ear",
|
|
427
|
+
"Summer Solstice",
|
|
428
|
+
"Minor Heat",
|
|
429
|
+
"Major Heat",
|
|
430
|
+
"Start of Autumn",
|
|
431
|
+
"End of Heat",
|
|
432
|
+
"White Dew",
|
|
433
|
+
"Autumn Equinox",
|
|
434
|
+
"Cold Dew",
|
|
435
|
+
"Frost's Descent",
|
|
436
|
+
"Start of Winter",
|
|
437
|
+
"Minor Snow",
|
|
438
|
+
"Major Snow",
|
|
439
|
+
"Winter Solstice",
|
|
440
|
+
"Minor Cold",
|
|
441
|
+
"Major Cold",
|
|
442
|
+
"Start of Spring",
|
|
443
|
+
"Rain Water",
|
|
444
|
+
"Awakening of Insects"
|
|
445
|
+
],
|
|
446
|
+
trucNames: ["Ki\u1EBFn", "Tr\u1EEB", "M\xE3n", "B\xECnh", "\u0110\u1ECBnh", "Ch\u1EA5p", "Ph\xE1", "Nguy", "Th\xE0nh", "Thu", "Khai", "B\u1EBF"],
|
|
447
|
+
elementRelationNames: ["Generates", "Generated By", "Overcomes", "Overcome By", "Same Element"],
|
|
448
|
+
trucQualityNames: ["Bad", "Neutral", "Good"]
|
|
449
|
+
},
|
|
450
|
+
ja: {
|
|
451
|
+
heavenlyStems: ["\u7532", "\u4E59", "\u4E19", "\u4E01", "\u620A", "\u5DF1", "\u5E9A", "\u8F9B", "\u58EC", "\u7678"],
|
|
452
|
+
earthlyBranches: ["\u5B50", "\u4E11", "\u5BC5", "\u536F", "\u8FB0", "\u5DF3", "\u5348", "\u672A", "\u7533", "\u9149", "\u620C", "\u4EA5"],
|
|
453
|
+
fiveElements: ["\u91D1", "\u6728", "\u6C34", "\u706B", "\u571F"],
|
|
454
|
+
zodiacAnimals: ["\u9F20", "\u725B", "\u864E", "\u514E", "\u7ADC", "\u86C7", "\u99AC", "\u7F8A", "\u733F", "\u9D8F", "\u72AC", "\u732A"],
|
|
455
|
+
// @deprecated Ngữ nghĩa không nhất quán giữa các locale (xem lunarMonthNames/solarMonthNames).
|
|
456
|
+
monthNames: ["1\u6708", "2\u6708", "3\u6708", "4\u6708", "5\u6708", "6\u6708", "7\u6708", "8\u6708", "9\u6708", "10\u6708", "11\u6708", "12\u6708"],
|
|
457
|
+
lunarMonthNames: ["\u65E7\u66A61\u6708", "\u65E7\u66A62\u6708", "\u65E7\u66A63\u6708", "\u65E7\u66A64\u6708", "\u65E7\u66A65\u6708", "\u65E7\u66A66\u6708", "\u65E7\u66A67\u6708", "\u65E7\u66A68\u6708", "\u65E7\u66A69\u6708", "\u65E7\u66A610\u6708", "\u65E7\u66A611\u6708", "\u65E7\u66A612\u6708"],
|
|
458
|
+
solarMonthNames: ["1\u6708", "2\u6708", "3\u6708", "4\u6708", "5\u6708", "6\u6708", "7\u6708", "8\u6708", "9\u6708", "10\u6708", "11\u6708", "12\u6708"],
|
|
459
|
+
weekDays: ["\u65E5", "\u6708", "\u706B", "\u6C34", "\u6728", "\u91D1", "\u571F"],
|
|
460
|
+
leapLabel: "\u958F",
|
|
461
|
+
yearLabel: "\u5E74",
|
|
462
|
+
monthLabel: "\u6708",
|
|
463
|
+
destiny: "\u547D",
|
|
464
|
+
solarTermNames: [
|
|
465
|
+
"\u6625\u5206",
|
|
466
|
+
"\u6E05\u660E",
|
|
467
|
+
"\u7A40\u96E8",
|
|
468
|
+
"\u7ACB\u590F",
|
|
469
|
+
"\u5C0F\u6E80",
|
|
470
|
+
"\u8292\u7A2E",
|
|
471
|
+
"\u590F\u81F3",
|
|
472
|
+
"\u5C0F\u6691",
|
|
473
|
+
"\u5927\u6691",
|
|
474
|
+
"\u7ACB\u79CB",
|
|
475
|
+
"\u51E6\u6691",
|
|
476
|
+
"\u767D\u9732",
|
|
477
|
+
"\u79CB\u5206",
|
|
478
|
+
"\u5BD2\u9732",
|
|
479
|
+
"\u971C\u964D",
|
|
480
|
+
"\u7ACB\u51AC",
|
|
481
|
+
"\u5C0F\u96EA",
|
|
482
|
+
"\u5927\u96EA",
|
|
483
|
+
"\u51AC\u81F3",
|
|
484
|
+
"\u5C0F\u5BD2",
|
|
485
|
+
"\u5927\u5BD2",
|
|
486
|
+
"\u7ACB\u6625",
|
|
487
|
+
"\u96E8\u6C34",
|
|
488
|
+
"\u5553\u87C4"
|
|
489
|
+
],
|
|
490
|
+
trucNames: ["\u5EFA", "\u9664", "\u6E80", "\u5E73", "\u5B9A", "\u57F7", "\u7834", "\u5371", "\u6210", "\u53CE", "\u958B", "\u9589"],
|
|
491
|
+
elementRelationNames: ["\u76F8\u751F", "\u88AB\u751F", "\u76F8\u514B", "\u88AB\u514B", "\u6BD4\u548C"],
|
|
492
|
+
trucQualityNames: ["\u51F6", "\u666E\u901A", "\u5409"]
|
|
493
|
+
},
|
|
494
|
+
ko: {
|
|
495
|
+
heavenlyStems: ["\uAC11", "\uC744", "\uBCD1", "\uC815", "\uBB34", "\uAE30", "\uACBD", "\uC2E0", "\uC784", "\uACC4"],
|
|
496
|
+
earthlyBranches: ["\uC790", "\uCD95", "\uC778", "\uBB18", "\uC9C4", "\uC0AC", "\uC624", "\uBBF8", "\uC2E0", "\uC720", "\uC220", "\uD574"],
|
|
497
|
+
fiveElements: ["\uAE08", "\uBAA9", "\uC218", "\uD654", "\uD1A0"],
|
|
498
|
+
zodiacAnimals: ["\uC950", "\uC18C", "\uD638\uB791\uC774", "\uD1A0\uB07C", "\uC6A9", "\uBC40", "\uB9D0", "\uC591", "\uC6D0\uC22D\uC774", "\uB2ED", "\uAC1C", "\uB3FC\uC9C0"],
|
|
499
|
+
// @deprecated Ngữ nghĩa không nhất quán giữa các locale (xem lunarMonthNames/solarMonthNames).
|
|
500
|
+
monthNames: ["1\uC6D4", "2\uC6D4", "3\uC6D4", "4\uC6D4", "5\uC6D4", "6\uC6D4", "7\uC6D4", "8\uC6D4", "9\uC6D4", "10\uC6D4", "11\uC6D4", "12\uC6D4"],
|
|
501
|
+
lunarMonthNames: ["\uC74C\uB825 1\uC6D4", "\uC74C\uB825 2\uC6D4", "\uC74C\uB825 3\uC6D4", "\uC74C\uB825 4\uC6D4", "\uC74C\uB825 5\uC6D4", "\uC74C\uB825 6\uC6D4", "\uC74C\uB825 7\uC6D4", "\uC74C\uB825 8\uC6D4", "\uC74C\uB825 9\uC6D4", "\uC74C\uB825 10\uC6D4", "\uC74C\uB825 11\uC6D4", "\uC74C\uB825 12\uC6D4"],
|
|
502
|
+
solarMonthNames: ["1\uC6D4", "2\uC6D4", "3\uC6D4", "4\uC6D4", "5\uC6D4", "6\uC6D4", "7\uC6D4", "8\uC6D4", "9\uC6D4", "10\uC6D4", "11\uC6D4", "12\uC6D4"],
|
|
503
|
+
weekDays: ["\uC77C", "\uC6D4", "\uD654", "\uC218", "\uBAA9", "\uAE08", "\uD1A0"],
|
|
504
|
+
leapLabel: "\uC724",
|
|
505
|
+
yearLabel: "\uB144",
|
|
506
|
+
monthLabel: "\uC6D4",
|
|
507
|
+
destiny: "\uBA85",
|
|
508
|
+
solarTermNames: [
|
|
509
|
+
"\uCD98\uBD84",
|
|
510
|
+
"\uCCAD\uBA85",
|
|
511
|
+
"\uACE1\uC6B0",
|
|
512
|
+
"\uC785\uD558",
|
|
513
|
+
"\uC18C\uB9CC",
|
|
514
|
+
"\uB9DD\uC885",
|
|
515
|
+
"\uD558\uC9C0",
|
|
516
|
+
"\uC18C\uC11C",
|
|
517
|
+
"\uB300\uC11C",
|
|
518
|
+
"\uC785\uCD94",
|
|
519
|
+
"\uCC98\uC11C",
|
|
520
|
+
"\uBC31\uB85C",
|
|
521
|
+
"\uCD94\uBD84",
|
|
522
|
+
"\uD55C\uB85C",
|
|
523
|
+
"\uC0C1\uAC15",
|
|
524
|
+
"\uC785\uB3D9",
|
|
525
|
+
"\uC18C\uC124",
|
|
526
|
+
"\uB300\uC124",
|
|
527
|
+
"\uB3D9\uC9C0",
|
|
528
|
+
"\uC18C\uD55C",
|
|
529
|
+
"\uB300\uD55C",
|
|
530
|
+
"\uC785\uCD98",
|
|
531
|
+
"\uC6B0\uC218",
|
|
532
|
+
"\uACBD\uCE69"
|
|
533
|
+
],
|
|
534
|
+
trucNames: ["\uAC74", "\uC81C", "\uB9CC", "\uD3C9", "\uC815", "\uC9D1", "\uD30C", "\uC704", "\uC131", "\uC218", "\uAC1C", "\uD3D0"],
|
|
535
|
+
elementRelationNames: ["\uC0C1\uC0DD", "\uD53C\uC0DD", "\uC0C1\uADF9", "\uD53C\uADF9", "\uBE44\uD654"],
|
|
536
|
+
trucQualityNames: ["\uD749", "\uBCF4\uD1B5", "\uAE38"]
|
|
537
|
+
}
|
|
538
|
+
};
|
|
539
|
+
function t(locale) {
|
|
540
|
+
return translations[locale];
|
|
541
|
+
}
|
|
542
|
+
function getZodiacAnimal(branchIndex, locale = "vi") {
|
|
543
|
+
return translations[locale].zodiacAnimals[branchIndex % 12];
|
|
544
|
+
}
|
|
545
|
+
function getWeekDayLabels(locale, firstDayOfWeek = 0) {
|
|
546
|
+
const { weekDays } = translations[locale];
|
|
547
|
+
return firstDayOfWeek === 0 ? [...weekDays] : [...weekDays.slice(1), weekDays[0]];
|
|
548
|
+
}
|
|
323
549
|
|
|
324
|
-
// src/core/
|
|
325
|
-
function
|
|
326
|
-
const stemIndex = (
|
|
327
|
-
const branchIndex = (
|
|
328
|
-
const
|
|
329
|
-
|
|
330
|
-
|
|
331
|
-
|
|
332
|
-
|
|
550
|
+
// src/core/can-chi.ts
|
|
551
|
+
function getDayCanChi(jd, locale = "vi") {
|
|
552
|
+
const stemIndex = (jd + 9) % 10;
|
|
553
|
+
const branchIndex = (jd + 1) % 12;
|
|
554
|
+
const { heavenlyStems, earthlyBranches } = t(locale);
|
|
555
|
+
return `${heavenlyStems[stemIndex]} ${earthlyBranches[branchIndex]}`;
|
|
556
|
+
}
|
|
557
|
+
function getMonthCanChi(lunarMonth, lunarYear, locale = "vi") {
|
|
558
|
+
const yearStemIndex = (lunarYear + 6) % 10;
|
|
559
|
+
const monthStemOffset = yearStemIndex % 5 * 2 + 2;
|
|
560
|
+
const monthStemIndex = (monthStemOffset + lunarMonth - 1) % 10;
|
|
561
|
+
const monthBranchIndex = (lunarMonth + 1) % 12;
|
|
562
|
+
const { heavenlyStems, earthlyBranches } = t(locale);
|
|
563
|
+
return `${heavenlyStems[monthStemIndex]} ${earthlyBranches[monthBranchIndex]}`;
|
|
564
|
+
}
|
|
565
|
+
function getHourCanChi(hour, dayJd, locale = "vi") {
|
|
566
|
+
const hourBranchIndex = Math.floor((hour + 1) / 2) % 12;
|
|
567
|
+
const dayStemIndex = (dayJd + 9) % 10;
|
|
568
|
+
const hourStemOffset = dayStemIndex % 5 * 2;
|
|
569
|
+
const hourStemIndex = (hourStemOffset + hourBranchIndex) % 10;
|
|
570
|
+
const { heavenlyStems, earthlyBranches } = t(locale);
|
|
571
|
+
return `${heavenlyStems[hourStemIndex]} ${earthlyBranches[hourBranchIndex]}`;
|
|
572
|
+
}
|
|
573
|
+
|
|
574
|
+
// src/utils/math.ts
|
|
575
|
+
function mod(n, m) {
|
|
576
|
+
return (n % m + m) % m;
|
|
577
|
+
}
|
|
578
|
+
|
|
579
|
+
// src/core/ngu-hanh.ts
|
|
580
|
+
var NAP_AM_ELEMENT_INDEX = [
|
|
581
|
+
0,
|
|
582
|
+
3,
|
|
583
|
+
1,
|
|
584
|
+
4,
|
|
585
|
+
0,
|
|
586
|
+
3,
|
|
587
|
+
2,
|
|
588
|
+
4,
|
|
589
|
+
0,
|
|
590
|
+
1,
|
|
591
|
+
2,
|
|
592
|
+
4,
|
|
593
|
+
3,
|
|
594
|
+
1,
|
|
595
|
+
2,
|
|
596
|
+
0,
|
|
597
|
+
3,
|
|
598
|
+
1,
|
|
599
|
+
4,
|
|
600
|
+
0,
|
|
601
|
+
3,
|
|
602
|
+
2,
|
|
603
|
+
4,
|
|
604
|
+
0,
|
|
605
|
+
1,
|
|
606
|
+
2,
|
|
607
|
+
4,
|
|
608
|
+
3,
|
|
609
|
+
1,
|
|
610
|
+
2
|
|
611
|
+
];
|
|
612
|
+
function getSexagenaryIndex(stemIndex, branchIndex) {
|
|
613
|
+
for (let i = 0; i < 60; i++) {
|
|
614
|
+
if (i % 10 === stemIndex && i % 12 === branchIndex) {
|
|
615
|
+
return i;
|
|
616
|
+
}
|
|
333
617
|
}
|
|
334
|
-
|
|
335
|
-
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
|
|
340
|
-
|
|
618
|
+
throw new RangeError(`Lichta: Invalid Can Chi combination (stem=${stemIndex}, chi=${branchIndex})`);
|
|
619
|
+
}
|
|
620
|
+
function getNapAmElementIndex(stemIndex, branchIndex) {
|
|
621
|
+
const sexagenaryIndex = getSexagenaryIndex(stemIndex, branchIndex);
|
|
622
|
+
return NAP_AM_ELEMENT_INDEX[Math.floor(sexagenaryIndex / 2)];
|
|
623
|
+
}
|
|
624
|
+
function getElementName(index, locale = "vi") {
|
|
625
|
+
return t(locale).fiveElements[mod(index, 5)];
|
|
341
626
|
}
|
|
342
|
-
function
|
|
627
|
+
function getDayElementIndex(jd) {
|
|
343
628
|
const stemIndex = (jd + 9) % 10;
|
|
344
629
|
const branchIndex = (jd + 1) % 12;
|
|
345
|
-
return
|
|
630
|
+
return getNapAmElementIndex(stemIndex, branchIndex);
|
|
631
|
+
}
|
|
632
|
+
function getDayElement(jd, locale = "vi") {
|
|
633
|
+
return getElementName(getDayElementIndex(jd), locale);
|
|
346
634
|
}
|
|
347
|
-
function
|
|
635
|
+
function getMonthElementIndex(lunarMonth, lunarYear) {
|
|
348
636
|
const yearStemIndex = (lunarYear + 6) % 10;
|
|
349
637
|
const monthStemOffset = yearStemIndex % 5 * 2 + 2;
|
|
350
638
|
const monthStemIndex = (monthStemOffset + lunarMonth - 1) % 10;
|
|
351
639
|
const monthBranchIndex = (lunarMonth + 1) % 12;
|
|
352
|
-
return
|
|
640
|
+
return getNapAmElementIndex(monthStemIndex, monthBranchIndex);
|
|
353
641
|
}
|
|
354
|
-
function
|
|
642
|
+
function getMonthElement(lunarMonth, lunarYear, locale = "vi") {
|
|
643
|
+
return getElementName(getMonthElementIndex(lunarMonth, lunarYear), locale);
|
|
644
|
+
}
|
|
645
|
+
function getHourElementIndex(hour, dayJd) {
|
|
355
646
|
const hourBranchIndex = Math.floor((hour + 1) / 2) % 12;
|
|
356
647
|
const dayStemIndex = (dayJd + 9) % 10;
|
|
357
648
|
const hourStemOffset = dayStemIndex % 5 * 2;
|
|
358
649
|
const hourStemIndex = (hourStemOffset + hourBranchIndex) % 10;
|
|
359
|
-
return
|
|
650
|
+
return getNapAmElementIndex(hourStemIndex, hourBranchIndex);
|
|
651
|
+
}
|
|
652
|
+
function getHourElement(hour, dayJd, locale = "vi") {
|
|
653
|
+
return getElementName(getHourElementIndex(hour, dayJd), locale);
|
|
654
|
+
}
|
|
655
|
+
var ELEMENT_SINH_TARGET = [2, 3, 1, 4, 0];
|
|
656
|
+
var ELEMENT_KHAC_TARGET = [1, 4, 3, 0, 2];
|
|
657
|
+
function getElementRelationIndex(fromIndex, toIndex) {
|
|
658
|
+
const a = mod(fromIndex, 5);
|
|
659
|
+
const b = mod(toIndex, 5);
|
|
660
|
+
if (a === b) return 4;
|
|
661
|
+
if (ELEMENT_SINH_TARGET[a] === b) return 0;
|
|
662
|
+
if (ELEMENT_SINH_TARGET[b] === a) return 1;
|
|
663
|
+
if (ELEMENT_KHAC_TARGET[a] === b) return 2;
|
|
664
|
+
return 3;
|
|
665
|
+
}
|
|
666
|
+
function getElementRelation(fromIndex, toIndex, locale = "vi") {
|
|
667
|
+
const { elementRelationNames } = t(locale);
|
|
668
|
+
return elementRelationNames[getElementRelationIndex(fromIndex, toIndex)];
|
|
669
|
+
}
|
|
670
|
+
|
|
671
|
+
// src/core/tiet-khi.ts
|
|
672
|
+
function getSolarTermName(index, locale = "vi") {
|
|
673
|
+
const { solarTermNames } = t(locale);
|
|
674
|
+
return solarTermNames[(index % 24 + 24) % 24];
|
|
675
|
+
}
|
|
676
|
+
function getSolarTerm(day, month, year, timeZone = 7, locale = "vi") {
|
|
677
|
+
const jd = jdFromDate(day, month, year);
|
|
678
|
+
const index = getSolarTermIndex(jd + 1, timeZone);
|
|
679
|
+
return { index, name: getSolarTermName(index, locale), date: { day, month, year }, jd };
|
|
680
|
+
}
|
|
681
|
+
var occurrencesCache = /* @__PURE__ */ new Map();
|
|
682
|
+
function getSolarTermOccurrencesInYear(year, timeZone) {
|
|
683
|
+
const cacheKey = `${year}:${timeZone}`;
|
|
684
|
+
const cached = occurrencesCache.get(cacheKey);
|
|
685
|
+
if (cached) return cached;
|
|
686
|
+
const startJd = jdFromDate(1, 1, year) - 5;
|
|
687
|
+
const endJd = jdFromDate(31, 12, year) + 5;
|
|
688
|
+
const occurrences = [];
|
|
689
|
+
let prevIndex = getSolarTermIndex(startJd, timeZone);
|
|
690
|
+
for (let jd = startJd + 1; jd <= endJd; jd++) {
|
|
691
|
+
const index = getSolarTermIndex(jd, timeZone);
|
|
692
|
+
if (index !== prevIndex) {
|
|
693
|
+
const termJd = jd - 1;
|
|
694
|
+
const [, , jdYear] = jdToDate(termJd);
|
|
695
|
+
if (jdYear === year) {
|
|
696
|
+
occurrences.push({ index, jd: termJd });
|
|
697
|
+
}
|
|
698
|
+
prevIndex = index;
|
|
699
|
+
}
|
|
700
|
+
}
|
|
701
|
+
occurrencesCache.set(cacheKey, occurrences);
|
|
702
|
+
return occurrences;
|
|
703
|
+
}
|
|
704
|
+
function getSolarTermsInYear(year, timeZone = 7, locale = "vi") {
|
|
705
|
+
return getSolarTermOccurrencesInYear(year, timeZone).map(({ index, jd }) => {
|
|
706
|
+
const [day, month, jdYear] = jdToDate(jd);
|
|
707
|
+
return { index, name: getSolarTermName(index, locale), date: { day, month, year: jdYear }, jd };
|
|
708
|
+
});
|
|
709
|
+
}
|
|
710
|
+
|
|
711
|
+
// src/core/truc-zodiac.ts
|
|
712
|
+
var TRUC_COUNT = 12;
|
|
713
|
+
function getTrucIndex(jd, timeZone = 7) {
|
|
714
|
+
const [, , year] = jdToDate(jd);
|
|
715
|
+
const tietTerms = [year - 1, year, year + 1].flatMap((y) => getSolarTermOccurrencesInYear(y, timeZone)).filter((term) => term.index % 2 === 1);
|
|
716
|
+
let governingTietJd = -Infinity;
|
|
717
|
+
for (const term of tietTerms) {
|
|
718
|
+
if (term.jd <= jd && term.jd > governingTietJd) {
|
|
719
|
+
governingTietJd = term.jd;
|
|
720
|
+
}
|
|
721
|
+
}
|
|
722
|
+
return mod(jd - governingTietJd, TRUC_COUNT);
|
|
723
|
+
}
|
|
724
|
+
function getTrucName(index, locale = "vi") {
|
|
725
|
+
const { trucNames } = t(locale);
|
|
726
|
+
return trucNames[mod(index, TRUC_COUNT)];
|
|
727
|
+
}
|
|
728
|
+
function getTruc(jd, timeZone = 7, locale = "vi") {
|
|
729
|
+
return getTrucName(getTrucIndex(jd, timeZone), locale);
|
|
730
|
+
}
|
|
731
|
+
var TRUC_QUALITY_INDEX = [1, 1, 1, 1, 1, 1, 0, 0, 2, 1, 2, 1];
|
|
732
|
+
function getTrucQualityIndex(trucIndex) {
|
|
733
|
+
return TRUC_QUALITY_INDEX[mod(trucIndex, TRUC_COUNT)];
|
|
734
|
+
}
|
|
735
|
+
function getTrucQuality(trucIndex, locale = "vi") {
|
|
736
|
+
const { trucQualityNames } = t(locale);
|
|
737
|
+
return trucQualityNames[getTrucQualityIndex(trucIndex)];
|
|
738
|
+
}
|
|
739
|
+
function getXungBranchIndex(branchIndex) {
|
|
740
|
+
return mod(branchIndex + 6, 12);
|
|
741
|
+
}
|
|
742
|
+
function isXung(branchIndexA, branchIndexB) {
|
|
743
|
+
return getXungBranchIndex(mod(branchIndexA, 12)) === mod(branchIndexB, 12);
|
|
744
|
+
}
|
|
745
|
+
var HAI_BRANCH_TARGET = [7, 6, 5, 4, 3, 2, 1, 0, 11, 10, 9, 8];
|
|
746
|
+
function getHaiBranchIndex(branchIndex) {
|
|
747
|
+
return HAI_BRANCH_TARGET[mod(branchIndex, 12)];
|
|
748
|
+
}
|
|
749
|
+
function isHai(branchIndexA, branchIndexB) {
|
|
750
|
+
return getHaiBranchIndex(mod(branchIndexA, 12)) === mod(branchIndexB, 12);
|
|
751
|
+
}
|
|
752
|
+
var TU_HANH_XUNG_GROUP = [0, 2, 1, 0, 2, 1, 0, 2, 1, 0, 2, 1];
|
|
753
|
+
var TU_HANH_XUNG_MEMBERS = [
|
|
754
|
+
[0, 3, 6, 9],
|
|
755
|
+
// Tý, Mão, Ngọ, Dậu
|
|
756
|
+
[2, 5, 8, 11],
|
|
757
|
+
// Dần, Tỵ, Thân, Hợi
|
|
758
|
+
[1, 4, 7, 10]
|
|
759
|
+
// Sửu, Thìn, Mùi, Tuất
|
|
760
|
+
];
|
|
761
|
+
function getTuHanhXungGroupIndex(branchIndex) {
|
|
762
|
+
return TU_HANH_XUNG_GROUP[mod(branchIndex, 12)];
|
|
763
|
+
}
|
|
764
|
+
function getTuHanhXungGroupMembers(branchIndex) {
|
|
765
|
+
return [...TU_HANH_XUNG_MEMBERS[getTuHanhXungGroupIndex(branchIndex)]];
|
|
766
|
+
}
|
|
767
|
+
function isTuHanhXung(branchIndexA, branchIndexB) {
|
|
768
|
+
const a = mod(branchIndexA, 12);
|
|
769
|
+
const b = mod(branchIndexB, 12);
|
|
770
|
+
return a !== b && getTuHanhXungGroupIndex(a) === getTuHanhXungGroupIndex(b);
|
|
771
|
+
}
|
|
772
|
+
function getZodiacConflicts(branchIndexA, branchIndexB) {
|
|
773
|
+
return {
|
|
774
|
+
xung: isXung(branchIndexA, branchIndexB),
|
|
775
|
+
hai: isHai(branchIndexA, branchIndexB),
|
|
776
|
+
tuHanhXung: isTuHanhXung(branchIndexA, branchIndexB)
|
|
777
|
+
};
|
|
778
|
+
}
|
|
779
|
+
|
|
780
|
+
// src/constants/five-elements.ts
|
|
781
|
+
var FIVE_ELEMENTS = ["Kim", "M\u1ED9c", "Th\u1EE7y", "H\u1ECFa", "Th\u1ED5"];
|
|
782
|
+
|
|
783
|
+
// src/core/almanac.ts
|
|
784
|
+
function getYearDetails(year) {
|
|
785
|
+
const stemIndex = mod(year - 4, 10);
|
|
786
|
+
const branchIndex = mod(year - 4, 12);
|
|
787
|
+
const elementIndex = getNapAmElementIndex(stemIndex, branchIndex);
|
|
788
|
+
return {
|
|
789
|
+
can: HEAVENLY_STEMS[stemIndex],
|
|
790
|
+
chi: EARTHLY_BRANCHES[branchIndex],
|
|
791
|
+
menh: FIVE_ELEMENTS[elementIndex],
|
|
792
|
+
menhIndex: elementIndex,
|
|
793
|
+
fullString: `${HEAVENLY_STEMS[stemIndex]} ${EARTHLY_BRANCHES[branchIndex]} - M\u1EC7nh ${FIVE_ELEMENTS[elementIndex]}`
|
|
794
|
+
};
|
|
360
795
|
}
|
|
361
796
|
var AUSPICIOUS_HOURS_TABLE = [
|
|
362
797
|
[0, 1, 3, 6, 7, 9],
|
|
@@ -372,11 +807,29 @@ var AUSPICIOUS_HOURS_TABLE = [
|
|
|
372
807
|
[2, 5, 6, 8, 11, 0]
|
|
373
808
|
// Ngày Tỵ (5) / Hợi (11)
|
|
374
809
|
];
|
|
375
|
-
function getAuspiciousHours(dayJd) {
|
|
810
|
+
function getAuspiciousHours(dayJd, locale = "vi") {
|
|
376
811
|
const branchIndex = (dayJd + 1) % 12;
|
|
377
812
|
const groupIndex = branchIndex % 6;
|
|
378
813
|
const hourIndices = AUSPICIOUS_HOURS_TABLE[groupIndex];
|
|
379
|
-
|
|
814
|
+
const { earthlyBranches } = t(locale);
|
|
815
|
+
return hourIndices.map((i) => earthlyBranches[i]);
|
|
816
|
+
}
|
|
817
|
+
function getAuspiciousHourIndices(dayJd) {
|
|
818
|
+
const branchIndex = (dayJd + 1) % 12;
|
|
819
|
+
const groupIndex = branchIndex % 6;
|
|
820
|
+
return [...AUSPICIOUS_HOURS_TABLE[groupIndex]];
|
|
821
|
+
}
|
|
822
|
+
function getInauspiciousHourIndices(dayJd) {
|
|
823
|
+
const auspicious = new Set(getAuspiciousHourIndices(dayJd));
|
|
824
|
+
const inauspicious = [];
|
|
825
|
+
for (let i = 0; i < 12; i++) {
|
|
826
|
+
if (!auspicious.has(i)) inauspicious.push(i);
|
|
827
|
+
}
|
|
828
|
+
return inauspicious;
|
|
829
|
+
}
|
|
830
|
+
function getInauspiciousHours(dayJd, locale = "vi") {
|
|
831
|
+
const { earthlyBranches } = t(locale);
|
|
832
|
+
return getInauspiciousHourIndices(dayJd).map((i) => earthlyBranches[i]);
|
|
380
833
|
}
|
|
381
834
|
|
|
382
835
|
// src/utils/format.ts
|
|
@@ -435,7 +888,7 @@ function getDayName(day) {
|
|
|
435
888
|
}
|
|
436
889
|
return "Ba M\u01B0\u01A1i";
|
|
437
890
|
}
|
|
438
|
-
function formatLunarDate(lunar, pattern) {
|
|
891
|
+
function formatLunarDate(lunar, pattern, locale = "vi") {
|
|
439
892
|
let result = pattern;
|
|
440
893
|
result = result.replace(/yyyy/g, String(lunar.year));
|
|
441
894
|
result = result.replace(/yy/g, String(lunar.year).slice(-2));
|
|
@@ -444,7 +897,7 @@ function formatLunarDate(lunar, pattern) {
|
|
|
444
897
|
result = result.replace(/CC/g, lunar.yearCanChi ?? "");
|
|
445
898
|
result = result.replace(/DC/g, lunar.dayCanChi ?? "");
|
|
446
899
|
result = result.replace(/MC/g, lunar.monthCanChi ?? "");
|
|
447
|
-
result = result.replace(/L/g, lunar.isLeap ?
|
|
900
|
+
result = result.replace(/L/g, lunar.isLeap ? t(locale).leapLabel : "");
|
|
448
901
|
result = result.replace(/(?<![0-9])d(?![0-9d])/g, String(lunar.day));
|
|
449
902
|
result = result.replace(/(?<![0-9])M(?![0-9MC])/g, String(lunar.month));
|
|
450
903
|
return result.trim();
|
|
@@ -457,76 +910,107 @@ function formatTraditional(lunar) {
|
|
|
457
910
|
return `${dayName} th\xE1ng ${monthName}${leapSuffix} n\u0103m ${yearCanChi}`.trim();
|
|
458
911
|
}
|
|
459
912
|
|
|
460
|
-
// src/
|
|
461
|
-
|
|
462
|
-
|
|
463
|
-
heavenlyStems: ["Gi\xE1p", "\u1EA4t", "B\xEDnh", "\u0110inh", "M\u1EADu", "K\u1EF7", "Canh", "T\xE2n", "Nh\xE2m", "Qu\xFD"],
|
|
464
|
-
earthlyBranches: ["T\xFD", "S\u1EEDu", "D\u1EA7n", "M\xE3o", "Th\xECn", "T\u1EF5", "Ng\u1ECD", "M\xF9i", "Th\xE2n", "D\u1EADu", "Tu\u1EA5t", "H\u1EE3i"],
|
|
465
|
-
fiveElements: ["Kim", "M\u1ED9c", "Th\u1EE7y", "H\u1ECFa", "Th\u1ED5"],
|
|
466
|
-
zodiacAnimals: ["Chu\u1ED9t", "Tr\xE2u", "C\u1ECDp", "Th\u1ECF", "R\u1ED3ng", "R\u1EAFn", "Ng\u1EF1a", "D\xEA", "Kh\u1EC9", "G\xE0", "Ch\xF3", "Heo"],
|
|
467
|
-
monthNames: ["Gi\xEAng", "Hai", "Ba", "T\u01B0", "N\u0103m", "S\xE1u", "B\u1EA3y", "T\xE1m", "Ch\xEDn", "M\u01B0\u1EDDi", "M\u1ED9t", "Ch\u1EA1p"],
|
|
468
|
-
weekDays: ["CN", "T2", "T3", "T4", "T5", "T6", "T7"],
|
|
469
|
-
leapLabel: "Nhu\u1EADn",
|
|
470
|
-
yearLabel: "N\u0103m",
|
|
471
|
-
monthLabel: "Th\xE1ng",
|
|
472
|
-
destiny: "M\u1EC7nh"
|
|
473
|
-
},
|
|
474
|
-
en: {
|
|
475
|
-
heavenlyStems: ["Gi\xE1p", "\u1EA4t", "B\xEDnh", "\u0110inh", "M\u1EADu", "K\u1EF7", "Canh", "T\xE2n", "Nh\xE2m", "Qu\xFD"],
|
|
476
|
-
earthlyBranches: ["T\xFD", "S\u1EEDu", "D\u1EA7n", "M\xE3o", "Th\xECn", "T\u1EF5", "Ng\u1ECD", "M\xF9i", "Th\xE2n", "D\u1EADu", "Tu\u1EA5t", "H\u1EE3i"],
|
|
477
|
-
fiveElements: ["Metal", "Wood", "Water", "Fire", "Earth"],
|
|
478
|
-
zodiacAnimals: ["Rat", "Ox", "Tiger", "Rabbit", "Dragon", "Snake", "Horse", "Goat", "Monkey", "Rooster", "Dog", "Pig"],
|
|
479
|
-
monthNames: ["January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"],
|
|
480
|
-
weekDays: ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"],
|
|
481
|
-
leapLabel: "Leap",
|
|
482
|
-
yearLabel: "Year",
|
|
483
|
-
monthLabel: "Month",
|
|
484
|
-
destiny: "Destiny"
|
|
485
|
-
},
|
|
486
|
-
ja: {
|
|
487
|
-
heavenlyStems: ["\u7532", "\u4E59", "\u4E19", "\u4E01", "\u620A", "\u5DF1", "\u5E9A", "\u8F9B", "\u58EC", "\u7678"],
|
|
488
|
-
earthlyBranches: ["\u5B50", "\u4E11", "\u5BC5", "\u536F", "\u8FB0", "\u5DF3", "\u5348", "\u672A", "\u7533", "\u9149", "\u620C", "\u4EA5"],
|
|
489
|
-
fiveElements: ["\u91D1", "\u6728", "\u6C34", "\u706B", "\u571F"],
|
|
490
|
-
zodiacAnimals: ["\u9F20", "\u725B", "\u864E", "\u514E", "\u7ADC", "\u86C7", "\u99AC", "\u7F8A", "\u733F", "\u9D8F", "\u72AC", "\u732A"],
|
|
491
|
-
monthNames: ["1\u6708", "2\u6708", "3\u6708", "4\u6708", "5\u6708", "6\u6708", "7\u6708", "8\u6708", "9\u6708", "10\u6708", "11\u6708", "12\u6708"],
|
|
492
|
-
weekDays: ["\u65E5", "\u6708", "\u706B", "\u6C34", "\u6728", "\u91D1", "\u571F"],
|
|
493
|
-
leapLabel: "\u958F",
|
|
494
|
-
yearLabel: "\u5E74",
|
|
495
|
-
monthLabel: "\u6708",
|
|
496
|
-
destiny: "\u547D"
|
|
497
|
-
},
|
|
498
|
-
ko: {
|
|
499
|
-
heavenlyStems: ["\uAC11", "\uC744", "\uBCD1", "\uC815", "\uBB34", "\uAE30", "\uACBD", "\uC2E0", "\uC784", "\uACC4"],
|
|
500
|
-
earthlyBranches: ["\uC790", "\uCD95", "\uC778", "\uBB18", "\uC9C4", "\uC0AC", "\uC624", "\uBBF8", "\uC2E0", "\uC720", "\uC220", "\uD574"],
|
|
501
|
-
fiveElements: ["\uAE08", "\uBAA9", "\uC218", "\uD654", "\uD1A0"],
|
|
502
|
-
zodiacAnimals: ["\uC950", "\uC18C", "\uD638\uB791\uC774", "\uD1A0\uB07C", "\uC6A9", "\uBC40", "\uB9D0", "\uC591", "\uC6D0\uC22D\uC774", "\uB2ED", "\uAC1C", "\uB3FC\uC9C0"],
|
|
503
|
-
monthNames: ["1\uC6D4", "2\uC6D4", "3\uC6D4", "4\uC6D4", "5\uC6D4", "6\uC6D4", "7\uC6D4", "8\uC6D4", "9\uC6D4", "10\uC6D4", "11\uC6D4", "12\uC6D4"],
|
|
504
|
-
weekDays: ["\uC77C", "\uC6D4", "\uD654", "\uC218", "\uBAA9", "\uAE08", "\uD1A0"],
|
|
505
|
-
leapLabel: "\uC724",
|
|
506
|
-
yearLabel: "\uB144",
|
|
507
|
-
monthLabel: "\uC6D4",
|
|
508
|
-
destiny: "\uBA85"
|
|
509
|
-
}
|
|
510
|
-
};
|
|
511
|
-
function t(locale) {
|
|
512
|
-
return translations[locale];
|
|
913
|
+
// src/utils/calendar-grid.ts
|
|
914
|
+
function dateKey(date) {
|
|
915
|
+
return `${date.getFullYear()}-${date.getMonth() + 1}-${date.getDate()}`;
|
|
513
916
|
}
|
|
514
|
-
function
|
|
515
|
-
|
|
917
|
+
function getISOWeekNumber(date) {
|
|
918
|
+
const d = new Date(Date.UTC(date.getFullYear(), date.getMonth(), date.getDate()));
|
|
919
|
+
const dayNum = (d.getUTCDay() + 6) % 7;
|
|
920
|
+
d.setUTCDate(d.getUTCDate() - dayNum + 3);
|
|
921
|
+
const firstThursday = new Date(Date.UTC(d.getUTCFullYear(), 0, 4));
|
|
922
|
+
const firstThursdayDayNum = (firstThursday.getUTCDay() + 6) % 7;
|
|
923
|
+
firstThursday.setUTCDate(firstThursday.getUTCDate() - firstThursdayDayNum + 3);
|
|
924
|
+
return 1 + Math.round((d.getTime() - firstThursday.getTime()) / 6048e5);
|
|
925
|
+
}
|
|
926
|
+
function getCalendarGrid(month, year, selectedDate, firstDayOfWeek = 0) {
|
|
927
|
+
const grid = [];
|
|
928
|
+
const firstDay = new Date(year, month - 1, 1);
|
|
929
|
+
const lastDay = new Date(year, month, 0);
|
|
930
|
+
const startingDayOfWeek = (firstDay.getDay() - firstDayOfWeek + 7) % 7;
|
|
931
|
+
const daysInMonth = lastDay.getDate();
|
|
932
|
+
const todayKey = dateKey(/* @__PURE__ */ new Date());
|
|
933
|
+
const selectedKey = selectedDate ? dateKey(selectedDate) : "";
|
|
934
|
+
const prevMonthLastDay = new Date(year, month - 1, 0).getDate();
|
|
935
|
+
const pushCell = (solar, d, m, y, isCurrentMonth) => {
|
|
936
|
+
grid.push({
|
|
937
|
+
solar,
|
|
938
|
+
lunar: LichTa.toLunar(d, m, y),
|
|
939
|
+
isToday: dateKey(solar) === todayKey,
|
|
940
|
+
isSelected: dateKey(solar) === selectedKey,
|
|
941
|
+
isCurrentMonth,
|
|
942
|
+
weekNumber: 0
|
|
943
|
+
// gán lại theo từng hàng ở bước cuối, xem vòng lặp bên dưới
|
|
944
|
+
});
|
|
945
|
+
};
|
|
946
|
+
for (let i = startingDayOfWeek - 1; i >= 0; i--) {
|
|
947
|
+
const d = prevMonthLastDay - i;
|
|
948
|
+
const m = month - 1 < 1 ? 12 : month - 1;
|
|
949
|
+
const y = month - 1 < 1 ? year - 1 : year;
|
|
950
|
+
pushCell(new Date(y, m - 1, d), d, m, y, false);
|
|
951
|
+
}
|
|
952
|
+
for (let d = 1; d <= daysInMonth; d++) {
|
|
953
|
+
pushCell(new Date(year, month - 1, d), d, month, year, true);
|
|
954
|
+
}
|
|
955
|
+
const remaining = 42 - grid.length;
|
|
956
|
+
for (let d = 1; d <= remaining; d++) {
|
|
957
|
+
const m = month + 1 > 12 ? 1 : month + 1;
|
|
958
|
+
const y = month + 1 > 12 ? year + 1 : year;
|
|
959
|
+
pushCell(new Date(y, m - 1, d), d, m, y, false);
|
|
960
|
+
}
|
|
961
|
+
const thursdayOffset = (4 - firstDayOfWeek + 7) % 7;
|
|
962
|
+
for (let row = 0; row < grid.length; row += 7) {
|
|
963
|
+
const weekNumber = getISOWeekNumber(grid[row + thursdayOffset].solar);
|
|
964
|
+
for (let i = row; i < row + 7; i++) {
|
|
965
|
+
grid[i].weekNumber = weekNumber;
|
|
966
|
+
}
|
|
967
|
+
}
|
|
968
|
+
return grid;
|
|
516
969
|
}
|
|
517
970
|
// Annotate the CommonJS export names for ESM import in node:
|
|
518
971
|
0 && (module.exports = {
|
|
519
972
|
LichTa,
|
|
520
973
|
formatLunarDate,
|
|
521
974
|
formatTraditional,
|
|
975
|
+
getAuspiciousHourIndices,
|
|
522
976
|
getAuspiciousHours,
|
|
977
|
+
getCalendarGrid,
|
|
523
978
|
getDayCanChi,
|
|
979
|
+
getDayElement,
|
|
980
|
+
getDayElementIndex,
|
|
524
981
|
getDayName,
|
|
982
|
+
getElementName,
|
|
983
|
+
getElementRelation,
|
|
984
|
+
getElementRelationIndex,
|
|
985
|
+
getHaiBranchIndex,
|
|
525
986
|
getHourCanChi,
|
|
987
|
+
getHourElement,
|
|
988
|
+
getHourElementIndex,
|
|
989
|
+
getISOWeekNumber,
|
|
990
|
+
getInauspiciousHourIndices,
|
|
991
|
+
getInauspiciousHours,
|
|
526
992
|
getMonthCanChi,
|
|
993
|
+
getMonthElement,
|
|
994
|
+
getMonthElementIndex,
|
|
527
995
|
getMonthName,
|
|
996
|
+
getSolarTerm,
|
|
997
|
+
getSolarTermName,
|
|
998
|
+
getSolarTermsInYear,
|
|
999
|
+
getTruc,
|
|
1000
|
+
getTrucIndex,
|
|
1001
|
+
getTrucName,
|
|
1002
|
+
getTrucQuality,
|
|
1003
|
+
getTrucQualityIndex,
|
|
1004
|
+
getTuHanhXungGroupIndex,
|
|
1005
|
+
getTuHanhXungGroupMembers,
|
|
1006
|
+
getWeekDayLabels,
|
|
1007
|
+
getXungBranchIndex,
|
|
528
1008
|
getYearDetails,
|
|
529
1009
|
getZodiacAnimal,
|
|
1010
|
+
getZodiacConflicts,
|
|
1011
|
+
isHai,
|
|
1012
|
+
isTuHanhXung,
|
|
1013
|
+
isXung,
|
|
530
1014
|
jdFromDate,
|
|
531
1015
|
jdToDate,
|
|
532
1016
|
t
|