@iftc/yete 0.0.1-alpha.5 → 0.0.1-alpha.6
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/index.js +237 -3
- package/package.json +1 -1
package/index.js
CHANGED
|
@@ -32,13 +32,17 @@ class YeteError extends Error {
|
|
|
32
32
|
} else if (/Version\/(\d+)/.test(ua) && /Safari/.test(ua)) {
|
|
33
33
|
browser = 'Safari';
|
|
34
34
|
version = parseInt(ua.match(/Version\/(\d+)/)[1], 10);
|
|
35
|
+
} else if (/VVBrowser\/(\d+)/.test(ua)) {
|
|
36
|
+
browser = 'VVBrowser';
|
|
37
|
+
version = parseInt(ua.match(/VVBrowser\/(\d+)/)[1], 10);
|
|
35
38
|
}
|
|
36
39
|
console.log(browser, version);
|
|
37
40
|
const minVersions = {
|
|
38
41
|
'Chrome': 87,
|
|
39
42
|
'Firefox': 140,
|
|
40
43
|
'Safari': 18.4,
|
|
41
|
-
'Edge': 87
|
|
44
|
+
'Edge': 87,
|
|
45
|
+
'VVBrowser': 1
|
|
42
46
|
};
|
|
43
47
|
let isCompatible = false;
|
|
44
48
|
if (browser && minVersions[browser] !== undefined) {
|
|
@@ -48,8 +52,8 @@ class YeteError extends Error {
|
|
|
48
52
|
}
|
|
49
53
|
if (!isCompatible) {
|
|
50
54
|
const msg = browser
|
|
51
|
-
? `您的浏览器版本过低 (${browser} ${version}),请使用 Chrome 71+, Firefox 69+, Safari 12.1+ 或
|
|
52
|
-
: `无法识别您的浏览器环境,请使用现代浏览器 (Chrome, Firefox, Safari, Edge)。`;
|
|
55
|
+
? `您的浏览器版本过低 (${browser} ${version}),请使用 Chrome 71+, Firefox 69+, Safari 12.1+, Edge 79+ 或 VVBrowser 1+ 浏览器。`
|
|
56
|
+
: `无法识别您的浏览器环境,请使用现代浏览器 (Chrome, Firefox, Safari, Edge, VVBrowser)。`;
|
|
53
57
|
|
|
54
58
|
alert(msg);
|
|
55
59
|
console.error(new YeteError('Browser incompatible'));
|
|
@@ -606,6 +610,26 @@ const obj = {
|
|
|
606
610
|
static async readHeaders(response) {
|
|
607
611
|
return response.headers;
|
|
608
612
|
}
|
|
613
|
+
/**
|
|
614
|
+
* 读取响应 Cookie
|
|
615
|
+
* @param {Response} response
|
|
616
|
+
* @returns {Promise<Cookie[]>}
|
|
617
|
+
* @example
|
|
618
|
+
* const cookies = await HTTP.readCookies(res);
|
|
619
|
+
*/
|
|
620
|
+
static async readCookies(response) {
|
|
621
|
+
return response.cookies;
|
|
622
|
+
}
|
|
623
|
+
/**
|
|
624
|
+
* 获取代理 URL
|
|
625
|
+
* @param {String} url
|
|
626
|
+
* @returns {String}
|
|
627
|
+
* @example
|
|
628
|
+
* const proxyURL = HTTP.proxy("https://example.com");
|
|
629
|
+
*/
|
|
630
|
+
static proxy(url) {
|
|
631
|
+
return "https://iftc.koyeb.app/proxy?url=" + encodeURIComponent(url);
|
|
632
|
+
}
|
|
609
633
|
},
|
|
610
634
|
/**
|
|
611
635
|
* 获取 URL 参数
|
|
@@ -918,8 +942,152 @@ const obj = {
|
|
|
918
942
|
location.reload();
|
|
919
943
|
}
|
|
920
944
|
},
|
|
945
|
+
Complex: Complex,
|
|
946
|
+
/**
|
|
947
|
+
* 屏幕颜色选择器
|
|
948
|
+
* @description 该功能必须由用户主动触发(如点击按钮)才行。
|
|
949
|
+
* @returns {Promise<string>} 十六进制颜色值(如#FF0000)
|
|
950
|
+
* @throws {YeteError} 如果用户取消了选择或浏览器不支持 EyeDropper API
|
|
951
|
+
* @example
|
|
952
|
+
* button.addEventListener('click', async () => {
|
|
953
|
+
* const color = await colorPicker();
|
|
954
|
+
* console.log(color);
|
|
955
|
+
* })
|
|
956
|
+
*/
|
|
957
|
+
colorPicker: function () {
|
|
958
|
+
if (!globalThis.EyeDropper) {
|
|
959
|
+
throw new YeteError("Your browser does not support the EyeDropper API. Please use a compatible browser (Chrome 95+, Edge 95+, or Opera 81+).");
|
|
960
|
+
}
|
|
961
|
+
const eyeDropper = new EyeDropper();
|
|
962
|
+
const abortController = new AbortController();
|
|
963
|
+
return eyeDropper.open({ signal: abortController.signal }).then(result => result.sRGBHex).catch(error => {
|
|
964
|
+
if (error.name === 'AbortError') {
|
|
965
|
+
throw new YeteError('用户取消了选择');
|
|
966
|
+
} else {
|
|
967
|
+
throw error;
|
|
968
|
+
}
|
|
969
|
+
});
|
|
970
|
+
}
|
|
921
971
|
};
|
|
922
972
|
|
|
973
|
+
/**
|
|
974
|
+
* 复数类
|
|
975
|
+
*/
|
|
976
|
+
class Complex {
|
|
977
|
+
/**
|
|
978
|
+
* 复数构造函数
|
|
979
|
+
* @param {number} real 实部
|
|
980
|
+
* @param {number} imag 虚部
|
|
981
|
+
*/
|
|
982
|
+
constructor(real = 0, imag = 0) {
|
|
983
|
+
this.real = real;
|
|
984
|
+
this.imag = imag;
|
|
985
|
+
}
|
|
986
|
+
/**
|
|
987
|
+
* 字符串转复数类
|
|
988
|
+
* @param {String} complexString
|
|
989
|
+
* @returns {Complex}
|
|
990
|
+
* @example
|
|
991
|
+
* const complex = new Complex();
|
|
992
|
+
* complex.toClass("2+3i"); // 输出:Complex(2, 3)
|
|
993
|
+
*/
|
|
994
|
+
toClass(complexString) {
|
|
995
|
+
const parts = complexString.split('+');
|
|
996
|
+
const real = parseFloat(parts[0]) || 0;
|
|
997
|
+
const imag = parseFloat(parts[1].slice(0, -1)) || 0;
|
|
998
|
+
this.real = real;
|
|
999
|
+
this.imag = imag;
|
|
1000
|
+
return this;
|
|
1001
|
+
}
|
|
1002
|
+
/**
|
|
1003
|
+
* 加法
|
|
1004
|
+
* @param {Complex} other 另一个复数
|
|
1005
|
+
* @returns {Complex} 结果
|
|
1006
|
+
* @example
|
|
1007
|
+
* const c1 = new Complex(2, 3);
|
|
1008
|
+
* const c2 = new Complex(1, 4);
|
|
1009
|
+
* console.log(c1.add(c2)); // 输出:Complex(3, 7)
|
|
1010
|
+
*/
|
|
1011
|
+
add(other) {
|
|
1012
|
+
return new Complex(
|
|
1013
|
+
this.real + other.real,
|
|
1014
|
+
this.imag + other.imag
|
|
1015
|
+
);
|
|
1016
|
+
}
|
|
1017
|
+
/**
|
|
1018
|
+
* 减法
|
|
1019
|
+
* @param {Complex} other 另一个复数
|
|
1020
|
+
* @returns {Complex} 减法结果
|
|
1021
|
+
* @example
|
|
1022
|
+
* const c1 = new Complex(2, 3);
|
|
1023
|
+
* const c2 = new Complex(1, 4);
|
|
1024
|
+
* console.log(c1.subtract(c2)); // 输出:Complex(1, -1)
|
|
1025
|
+
*/
|
|
1026
|
+
subtract(other) {
|
|
1027
|
+
return new Complex(
|
|
1028
|
+
this.real - other.real,
|
|
1029
|
+
this.imag - other.imag
|
|
1030
|
+
);
|
|
1031
|
+
}
|
|
1032
|
+
/**
|
|
1033
|
+
* 乘法
|
|
1034
|
+
* @param {Complex} other 乘数
|
|
1035
|
+
* @returns {Complex} 乘法结果
|
|
1036
|
+
* @example
|
|
1037
|
+
* const c1 = new Complex(2, 3);
|
|
1038
|
+
* const c2 = new Complex(1, 4);
|
|
1039
|
+
* console.log(c1.multiply(c2)); // 输出:Complex(5, 14)
|
|
1040
|
+
*/
|
|
1041
|
+
multiply(other) {
|
|
1042
|
+
return new Complex(
|
|
1043
|
+
this.real * other.real - this.imag * other.imag,
|
|
1044
|
+
this.real * other.imag + this.imag * other.real
|
|
1045
|
+
);
|
|
1046
|
+
}
|
|
1047
|
+
/**
|
|
1048
|
+
* 除法
|
|
1049
|
+
* @param {Complex} other 被除数
|
|
1050
|
+
* @returns {Complex} 除法结果
|
|
1051
|
+
* @example
|
|
1052
|
+
* const c1 = new Complex(2, 3);
|
|
1053
|
+
* const c2 = new Complex(1, 4);
|
|
1054
|
+
* console.log(c1.divide(c2)); // 输出:Complex(0.6, -0.2)
|
|
1055
|
+
*/
|
|
1056
|
+
divide(other) {
|
|
1057
|
+
const denominator = other.real * other.real + other.imag * other.imag;
|
|
1058
|
+
if (denominator === 0) {
|
|
1059
|
+
throw new Error("Division by zero complex number");
|
|
1060
|
+
}
|
|
1061
|
+
return new Complex(
|
|
1062
|
+
(this.real * other.real + this.imag * other.imag) / denominator,
|
|
1063
|
+
(this.imag * other.real - this.real * other.imag) / denominator
|
|
1064
|
+
);
|
|
1065
|
+
}
|
|
1066
|
+
/**
|
|
1067
|
+
* 复数转为字符串
|
|
1068
|
+
* @returns {string} 复数字符串表示
|
|
1069
|
+
* @example
|
|
1070
|
+
* const c = new Complex(2, 3);
|
|
1071
|
+
* console.log(c.toString()); // 输出:2+3i
|
|
1072
|
+
*/
|
|
1073
|
+
toString() {
|
|
1074
|
+
const sign = this.imag >= 0 ? '+' : '-';
|
|
1075
|
+
return `${this.real} ${sign} ${Math.abs(this.imag)}i`;
|
|
1076
|
+
}
|
|
1077
|
+
/**
|
|
1078
|
+
* 获取复数的模
|
|
1079
|
+
* @returns {number} 模
|
|
1080
|
+
* @example
|
|
1081
|
+
* const c = new Complex(3, 4);
|
|
1082
|
+
* console.log(c.magnitude()); // 输出:5
|
|
1083
|
+
*/
|
|
1084
|
+
magnitude() {
|
|
1085
|
+
return Math.sqrt(this.real * this.real + this.imag * this.imag);
|
|
1086
|
+
}
|
|
1087
|
+
}
|
|
1088
|
+
|
|
1089
|
+
obj.Complex = Complex;
|
|
1090
|
+
|
|
923
1091
|
/**
|
|
924
1092
|
* 生成哈希值
|
|
925
1093
|
* @description 与Java的用法一致
|
|
@@ -937,6 +1105,72 @@ String.prototype.hashCode = function () {
|
|
|
937
1105
|
return hash;
|
|
938
1106
|
};
|
|
939
1107
|
|
|
1108
|
+
/**
|
|
1109
|
+
* 将任意进制的数字转换为十进制(支持小数)
|
|
1110
|
+
* @param {Number} fromRadix - 源进制 (2-36)
|
|
1111
|
+
* @param {Number} toRadix - 目标进制 (2-36)
|
|
1112
|
+
* @returns {String} - 转换后的目标进制的字符串
|
|
1113
|
+
* @example
|
|
1114
|
+
* const result = "10.1".convertBase(2, 10); // 二进制 "10.1" 转换为十进制 "2.5"
|
|
1115
|
+
*/
|
|
1116
|
+
String.prototype.convertBase = function (fromRadix = 10, toRadix = 10) {
|
|
1117
|
+
return convertBase(this, fromRadix, toRadix);
|
|
1118
|
+
};
|
|
1119
|
+
|
|
1120
|
+
/**
|
|
1121
|
+
* 将任意进制的数字转换为另一种进制的数字
|
|
1122
|
+
* @param {string} numStr - 输入的数字字符串(例如 "10.1")
|
|
1123
|
+
* @param {number} fromRadix - 源进制 (2-36)
|
|
1124
|
+
* @param {number} toRadix - 目标进制 (2-36)
|
|
1125
|
+
* @returns {string} - 转换后的字符串
|
|
1126
|
+
*/
|
|
1127
|
+
function convertBase(numStr, fromRadix, toRadix) {
|
|
1128
|
+
if (fromRadix < 2 || fromRadix > 36 || toRadix < 2 || toRadix > 36) {
|
|
1129
|
+
throw new YeteError("进制必须在 2 到 36 之间");
|
|
1130
|
+
}
|
|
1131
|
+
const decimalValue = convertToDecimal(numStr, fromRadix);
|
|
1132
|
+
return decimalValue.toString(toRadix);
|
|
1133
|
+
}
|
|
1134
|
+
|
|
1135
|
+
/**
|
|
1136
|
+
* 将任意进制(2-36)的字符串转换为十进制数字(支持小数)
|
|
1137
|
+
* @param {string} str - 输入的数字字符串 (例如 "10.1")
|
|
1138
|
+
* @param {number} radix - 进制数 (例如 2, 8, 16)
|
|
1139
|
+
* @returns {number} - 转换后的十进制数
|
|
1140
|
+
*/
|
|
1141
|
+
function convertToDecimal(str, radix) {
|
|
1142
|
+
if (radix < 2 || radix > 36) {
|
|
1143
|
+
throw new YeteError("进制必须在 2 到 36 之间");
|
|
1144
|
+
}
|
|
1145
|
+
const input = str.toLowerCase();
|
|
1146
|
+
const parts = input.split('.');
|
|
1147
|
+
const integerPart = parts[0];
|
|
1148
|
+
const fractionalPart = parts[1] || '';
|
|
1149
|
+
let result = 0;
|
|
1150
|
+
let isNegative = input.startsWith('-');
|
|
1151
|
+
if (integerPart && integerPart !== '-') {
|
|
1152
|
+
const cleanInt = integerPart.replace('-', '');
|
|
1153
|
+
result = parseInt(cleanInt, radix);
|
|
1154
|
+
if (isNaN(result)) {
|
|
1155
|
+
throw new YeteError(`整数部分 "${integerPart}" 包含非法字符`);
|
|
1156
|
+
}
|
|
1157
|
+
}
|
|
1158
|
+
let fractionValue = 0;
|
|
1159
|
+
for (let i = 0; i < fractionalPart.length; i++) {
|
|
1160
|
+
const char = fractionalPart[i];
|
|
1161
|
+
const digitValue = parseInt(char, 36);
|
|
1162
|
+
if (isNaN(digitValue) || digitValue >= radix) {
|
|
1163
|
+
throw new YeteError(`小数部分 "${char}" 超出了进制 ${radix} 的范围`);
|
|
1164
|
+
}
|
|
1165
|
+
fractionValue += digitValue * Math.pow(radix, -(i + 1));
|
|
1166
|
+
}
|
|
1167
|
+
result = result + fractionValue;
|
|
1168
|
+
if (isNegative) {
|
|
1169
|
+
result = -result;
|
|
1170
|
+
}
|
|
1171
|
+
return result;
|
|
1172
|
+
}
|
|
1173
|
+
|
|
940
1174
|
/**
|
|
941
1175
|
* 响应事件监听
|
|
942
1176
|
*/
|