@uxda/appkit 4.3.6 → 4.3.7

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/dist/index.js CHANGED
@@ -1719,13 +1719,30 @@ var script$F = /* @__PURE__ */ defineComponent({
1719
1719
  const $http = useHttp$3(), $n = useNutshell();
1720
1720
  const emits = __emit;
1721
1721
  const props = __props;
1722
- async function onUploadFile(csRes) {
1722
+ function getFileType(filePath, fileName) {
1723
+ const lowerPath = filePath.toLowerCase();
1724
+ const lowerName = (fileName || "").toLowerCase();
1725
+ if (lowerPath.endsWith(".pdf") || lowerName.endsWith(".pdf")) {
1726
+ return "pdf";
1727
+ }
1728
+ const imageExtensions = [".jpg", ".jpeg", ".png", ".gif", ".bmp", ".webp"];
1729
+ if (imageExtensions.some((ext) => lowerPath.endsWith(ext) || lowerName.endsWith(ext))) {
1730
+ return "img";
1731
+ }
1732
+ return "img";
1733
+ }
1734
+ async function onUploadFile(csRes, fileType) {
1723
1735
  try {
1724
- let { path, size, tempFilePath } = csRes.tempFiles[0];
1725
- const compressImg = await compressImage(path || tempFilePath, getCompressQuality(size)) || {};
1726
- const filePath = compressImg.tempFilePath || path;
1736
+ let { path, size, tempFilePath, name } = csRes.tempFiles[0];
1737
+ const originalPath = path || tempFilePath;
1738
+ const detectedFileType = fileType || getFileType(originalPath, name);
1739
+ let filePath = originalPath;
1740
+ if (detectedFileType === "img") {
1741
+ const compressImg = await compressImage(originalPath, getCompressQuality(size)) || {};
1742
+ filePath = compressImg.tempFilePath || originalPath;
1743
+ }
1727
1744
  if (props.customUpload) {
1728
- props.customUpload(filePath);
1745
+ props.customUpload(filePath, detectedFileType);
1729
1746
  return;
1730
1747
  }
1731
1748
  showLoading({ title: "\u53D1\u7968\u8BC6\u522B\u4E2D..", mask: true });
@@ -1745,7 +1762,7 @@ var script$F = /* @__PURE__ */ defineComponent({
1745
1762
  });
1746
1763
  const res = JSON.parse(upRes.data);
1747
1764
  if (res.code === "200") {
1748
- await getOcrInfo(res.result);
1765
+ await getOcrInfo(res.result, detectedFileType);
1749
1766
  } else {
1750
1767
  hideLoading();
1751
1768
  showToast({
@@ -1758,17 +1775,18 @@ var script$F = /* @__PURE__ */ defineComponent({
1758
1775
  console.log(err);
1759
1776
  }
1760
1777
  }
1761
- async function getOcrInfo(file) {
1778
+ async function getOcrInfo(file, fileType = "img") {
1762
1779
  try {
1780
+ const fileUrl = typeof file === "string" ? file : file.originalUrl;
1763
1781
  const res = await $http.get("/hkbase/common/vatInvoice", {
1764
- fileUrl: typeof file === "string" ? file : file.originalUrl,
1765
- fileType: "img"
1782
+ fileUrl,
1783
+ fileType
1766
1784
  });
1767
1785
  hideLoading();
1768
1786
  if (!res?.purchaserRegisterNum) {
1769
1787
  $n.dialog({
1770
1788
  title: "\u8BC6\u522B\u5931\u8D25",
1771
- message: `\u60A8\u4E0A\u4F20\u7684\u56FE\u7247\u53EF\u80FD\u4E0D\u591F\u6E05\u6670\u6216\u4E0E\u5F53\u524D\u529F\u80FD\u4E0D\u7B26\uFF0C\u8BF7\u91CD\u65B0\u4E0A\u4F20\u4E00\u5F20\u6E05\u6670\u3001\u5B8C\u6574\u7684\u56FE\u7247\u3002\u8C22\u8C22\uFF01`,
1789
+ message: `\u60A8\u4E0A\u4F20\u7684${fileType === "pdf" ? "\u6587\u4EF6" : "\u56FE\u7247"}\u53EF\u80FD\u4E0D\u591F\u6E05\u6670\u6216\u4E0E\u5F53\u524D\u529F\u80FD\u4E0D\u7B26\uFF0C\u8BF7\u91CD\u65B0\u4E0A\u4F20\u4E00\u5F20\u6E05\u6670\u3001\u5B8C\u6574\u7684${fileType === "pdf" ? "PDF\u6587\u4EF6" : "\u56FE\u7247"}\u3002\u8C22\u8C22\uFF01`,
1772
1790
  okText: "\u6211\u77E5\u9053\u4E86",
1773
1791
  cancelText: ""
1774
1792
  });
@@ -1789,7 +1807,8 @@ var script$F = /* @__PURE__ */ defineComponent({
1789
1807
  serviceType: res?.serviceType,
1790
1808
  totalAmount: res?.totalAmount,
1791
1809
  totalTax: res?.totalTax,
1792
- fileUrl: typeof file === "string" ? file : file.originalUrl,
1810
+ fileUrl,
1811
+ fileType,
1793
1812
  fileKey: typeof file === "string" ? file : file.fileId
1794
1813
  });
1795
1814
  } catch (err) {
@@ -1809,10 +1828,14 @@ var script$F = /* @__PURE__ */ defineComponent({
1809
1828
  {
1810
1829
  name: "\u4ECE\u804A\u5929\u4F1A\u8BDD\u9009\u62E9",
1811
1830
  type: "message"
1831
+ },
1832
+ {
1833
+ name: "\u9009\u62E9\u6587\u4EF6",
1834
+ type: "file"
1812
1835
  }
1813
1836
  ];
1814
1837
  if (Taro.getEnv() === "WEB") {
1815
- actionSheetMenus.pop();
1838
+ actionSheetMenus.splice(2, 1);
1816
1839
  }
1817
1840
  async function chooseImages(item) {
1818
1841
  if (["camera", "album"].includes(item.type)) {
@@ -1824,25 +1847,72 @@ var script$F = /* @__PURE__ */ defineComponent({
1824
1847
  // 使用duration属性判断是图片还是视频,图片没有该属性
1825
1848
  });
1826
1849
  onUploadFile(csRes);
1827
- } else {
1850
+ } else if (item.type === "message") {
1828
1851
  const csRes = await chooseMessageFile({
1829
1852
  count: 1,
1830
1853
  type: "image"
1831
1854
  });
1832
1855
  onUploadFile(csRes);
1856
+ } else if (item.type === "file") {
1857
+ const csRes = await chooseMessageFile({
1858
+ count: 1,
1859
+ type: "file"
1860
+ });
1861
+ onUploadFile(csRes);
1833
1862
  }
1834
1863
  }
1864
+ function chooseFileInWeb() {
1865
+ return new Promise((resolve, reject) => {
1866
+ const input = document.createElement("input");
1867
+ input.type = "file";
1868
+ input.accept = "image/*,.pdf";
1869
+ input.style.display = "none";
1870
+ input.onchange = async (e) => {
1871
+ const file = e.target?.files?.[0];
1872
+ if (!file) {
1873
+ document.body.removeChild(input);
1874
+ resolve();
1875
+ return;
1876
+ }
1877
+ let fileType = "img";
1878
+ if (file.type === "application/pdf" || file.name.toLowerCase().endsWith(".pdf")) {
1879
+ fileType = "pdf";
1880
+ }
1881
+ const filePath = URL.createObjectURL(file);
1882
+ try {
1883
+ const csRes = {
1884
+ tempFiles: [{
1885
+ path: filePath,
1886
+ tempFilePath: filePath,
1887
+ size: file.size,
1888
+ name: file.name
1889
+ }]
1890
+ };
1891
+ await onUploadFile(csRes, fileType);
1892
+ resolve();
1893
+ } catch (error) {
1894
+ reject(error);
1895
+ } finally {
1896
+ document.body.removeChild(input);
1897
+ URL.revokeObjectURL(filePath);
1898
+ }
1899
+ };
1900
+ input.oncancel = () => {
1901
+ document.body.removeChild(input);
1902
+ resolve();
1903
+ };
1904
+ document.body.appendChild(input);
1905
+ input.click();
1906
+ });
1907
+ }
1835
1908
  async function onUpload() {
1836
1909
  if (props.disabled) return;
1837
1910
  if (Taro.getEnv() === "WEB") {
1838
- const csRes = await chooseMedia({
1839
- count: 1,
1840
- sourceType: ["album"],
1841
- // "camera" | "album"
1842
- maxDuration: 60
1843
- // 使用duration属性判断是图片还是视频,图片没有该属性
1844
- });
1845
- onUploadFile(csRes);
1911
+ try {
1912
+ await chooseFileInWeb();
1913
+ } catch (err) {
1914
+ console.error("\u6587\u4EF6\u9009\u62E9\u5931\u8D25:", err);
1915
+ }
1846
1916
  return;
1847
1917
  }
1848
1918
  activeSheetVisible.value = true;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@uxda/appkit",
3
- "version": "4.3.6",
3
+ "version": "4.3.7",
4
4
  "description": "小程序应用开发包",
5
5
  "main": "dist/index.js",
6
6
  "module": "dist/index.ts",
@@ -49,14 +49,45 @@ const props = withDefaults(defineProps<OcrProps>(), {
49
49
  customClick: false
50
50
  })
51
51
 
52
- async function onUploadFile(csRes: any) {
52
+ /**
53
+ * 判断文件类型
54
+ */
55
+ function getFileType(filePath: string, fileName?: string): 'img' | 'pdf' {
56
+ const lowerPath = filePath.toLowerCase()
57
+ const lowerName = (fileName || '').toLowerCase()
58
+
59
+ // 检查文件扩展名
60
+ if (lowerPath.endsWith('.pdf') || lowerName.endsWith('.pdf')) {
61
+ return 'pdf'
62
+ }
63
+
64
+ // 检查是否为图片格式
65
+ const imageExtensions = ['.jpg', '.jpeg', '.png', '.gif', '.bmp', '.webp']
66
+ if (imageExtensions.some(ext => lowerPath.endsWith(ext) || lowerName.endsWith(ext))) {
67
+ return 'img'
68
+ }
69
+
70
+ // 默认为图片
71
+ return 'img'
72
+ }
73
+
74
+ async function onUploadFile(csRes: any, fileType?: 'img' | 'pdf') {
53
75
  try {
54
- let { path, size, tempFilePath } = csRes.tempFiles[0]
55
- const compressImg: any = (await compressImage(path || tempFilePath, getCompressQuality(size))) || {}
56
- const filePath = compressImg.tempFilePath || path
76
+ let { path, size, tempFilePath, name } = csRes.tempFiles[0]
77
+ const originalPath = path || tempFilePath
78
+
79
+ // 判断文件类型
80
+ const detectedFileType = fileType || getFileType(originalPath, name)
81
+
82
+ // 只有图片才进行压缩
83
+ let filePath = originalPath
84
+ if (detectedFileType === 'img') {
85
+ const compressImg: any = (await compressImage(originalPath, getCompressQuality(size))) || {}
86
+ filePath = compressImg.tempFilePath || originalPath
87
+ }
57
88
 
58
89
  if (props.customUpload) {
59
- props.customUpload(filePath)
90
+ props.customUpload(filePath, detectedFileType)
60
91
  return
61
92
  }
62
93
 
@@ -79,7 +110,7 @@ async function onUploadFile(csRes: any) {
79
110
 
80
111
  const res = JSON.parse(upRes.data)
81
112
  if (res.code === '200') {
82
- await getOcrInfo(res.result)
113
+ await getOcrInfo(res.result, detectedFileType)
83
114
  } else {
84
115
  hideLoading()
85
116
  showToast({
@@ -94,18 +125,19 @@ async function onUploadFile(csRes: any) {
94
125
  }
95
126
 
96
127
  // 根据证件路径获取证件信息
97
- async function getOcrInfo(file: string | FileType) {
128
+ async function getOcrInfo(file: string | FileType, fileType: 'img' | 'pdf' = 'img') {
98
129
  try {
130
+ const fileUrl = typeof file === 'string' ? file : file.originalUrl
99
131
  const res: any = await $http.get('/hkbase/common/vatInvoice', {
100
- fileUrl: typeof file === 'string' ? file : file.originalUrl,
101
- fileType: 'img'
132
+ fileUrl,
133
+ fileType: fileType
102
134
  })
103
135
  hideLoading()
104
136
 
105
137
  if (!res?.purchaserRegisterNum) {
106
138
  $n.dialog({
107
139
  title: '识别失败',
108
- message: `您上传的图片可能不够清晰或与当前功能不符,请重新上传一张清晰、完整的图片。谢谢!`,
140
+ message: `您上传的${fileType === 'pdf' ? '文件' : '图片'}可能不够清晰或与当前功能不符,请重新上传一张清晰、完整的${fileType === 'pdf' ? 'PDF文件' : '图片'}。谢谢!`,
109
141
  okText: '我知道了',
110
142
  cancelText: '',
111
143
  })
@@ -127,7 +159,8 @@ async function getOcrInfo(file: string | FileType) {
127
159
  serviceType: res?.serviceType,
128
160
  totalAmount: res?.totalAmount,
129
161
  totalTax: res?.totalTax,
130
- fileUrl: typeof file === 'string' ? file : file.originalUrl,
162
+ fileUrl: fileUrl,
163
+ fileType: fileType,
131
164
  fileKey: typeof file === 'string' ? file : file.fileId,
132
165
  })
133
166
  } catch (err) {
@@ -150,9 +183,14 @@ const actionSheetMenus = [
150
183
  name: '从聊天会话选择',
151
184
  type: 'message',
152
185
  },
186
+ {
187
+ name: '选择文件',
188
+ type: 'file',
189
+ },
153
190
  ]
154
191
  if (Taro.getEnv() === 'WEB') {
155
- actionSheetMenus.pop()
192
+ // Web 端移除"从聊天会话选择",保留"选择文件"
193
+ actionSheetMenus.splice(2, 1)
156
194
  }
157
195
 
158
196
  // 选择图像上传
@@ -165,27 +203,93 @@ async function chooseImages(item: any) {
165
203
  })
166
204
 
167
205
  onUploadFile(csRes)
168
- } else {
206
+ } else if (item.type === 'message') {
169
207
  const csRes = await chooseMessageFile({
170
208
  count: 1,
171
209
  type: 'image',
172
210
  })
173
211
 
212
+ onUploadFile(csRes)
213
+ } else if (item.type === 'file') {
214
+ // 选择文件(包括PDF)
215
+ const csRes = await chooseMessageFile({
216
+ count: 1,
217
+ type: 'file',
218
+ })
219
+
220
+ // 不预先指定类型,让 onUploadFile 根据文件名自动判断
174
221
  onUploadFile(csRes)
175
222
  }
176
223
  }
177
224
 
225
+ /**
226
+ * Web 端选择文件(支持图片和PDF)
227
+ */
228
+ function chooseFileInWeb() {
229
+ return new Promise<void>((resolve, reject) => {
230
+ const input = document.createElement('input')
231
+ input.type = 'file'
232
+ input.accept = 'image/*,.pdf'
233
+ input.style.display = 'none'
234
+
235
+ input.onchange = async (e: any) => {
236
+ const file = e.target?.files?.[0]
237
+ if (!file) {
238
+ document.body.removeChild(input)
239
+ resolve()
240
+ return
241
+ }
242
+
243
+ // 根据文件 MIME 类型和扩展名判断文件类型
244
+ let fileType: 'img' | 'pdf' = 'img'
245
+ if (file.type === 'application/pdf' || file.name.toLowerCase().endsWith('.pdf')) {
246
+ fileType = 'pdf'
247
+ }
248
+
249
+ const filePath = URL.createObjectURL(file)
250
+
251
+ try {
252
+ // 构造类似 chooseMedia 返回的数据结构
253
+ const csRes = {
254
+ tempFiles: [{
255
+ path: filePath,
256
+ tempFilePath: filePath,
257
+ size: file.size,
258
+ name: file.name,
259
+ }]
260
+ }
261
+
262
+ await onUploadFile(csRes, fileType)
263
+ resolve()
264
+ } catch (error) {
265
+ reject(error)
266
+ } finally {
267
+ document.body.removeChild(input)
268
+ // 清理 blob URL
269
+ URL.revokeObjectURL(filePath)
270
+ }
271
+ }
272
+
273
+ input.oncancel = () => {
274
+ document.body.removeChild(input)
275
+ resolve()
276
+ }
277
+
278
+ document.body.appendChild(input)
279
+ input.click()
280
+ })
281
+ }
282
+
178
283
  async function onUpload() {
179
284
  if (props.disabled) return
180
285
 
181
286
  if (Taro.getEnv() === 'WEB') {
182
- const csRes = await chooseMedia({
183
- count: 1,
184
- sourceType: ['album'], // "camera" | "album"
185
- maxDuration: 60, // 使用duration属性判断是图片还是视频,图片没有该属性
186
- })
187
-
188
- onUploadFile(csRes)
287
+ // Web 端弹出选择:图片或PDF
288
+ try {
289
+ await chooseFileInWeb()
290
+ } catch (err) {
291
+ console.error('文件选择失败:', err)
292
+ }
189
293
  return
190
294
  }
191
295