index.js 6.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212
  1. import * as XLSX from 'xlsx'
  2. import { ElMessage } from 'element-plus'
  3. import html2canvas from 'html2canvas'
  4. export function getPageInfo() {
  5. return new Promise((res, rej) => {
  6. chrome.runtime.sendMessage(
  7. {
  8. type: 'FROM_SIDE_PANEL_TO_GET_PAGE_INFO',
  9. },
  10. (response) => {
  11. if (chrome.runtime.lastError) {
  12. console.error('消息发送错误:', chrome.runtime.lastError, 555)
  13. rej(chrome.runtime.lastError)
  14. } else {
  15. res(response.data)
  16. }
  17. }
  18. )
  19. })
  20. }
  21. export function getPageInfoClean() {
  22. return new Promise((res, rej) => {
  23. chrome.runtime.sendMessage(
  24. {
  25. type: 'FROM_SIDE_PANEL_TO_GET_PAGE_INFO_CLEAN',
  26. },
  27. (response) => {
  28. if (chrome.runtime.lastError) {
  29. console.error('消息发送错误:', chrome.runtime.lastError, 555)
  30. rej(chrome.runtime.lastError)
  31. } else {
  32. res(response.data)
  33. }
  34. }
  35. )
  36. })
  37. }
  38. export function getPageInfoClean() {
  39. return new Promise((res, rej) => {
  40. chrome.runtime.sendMessage(
  41. {
  42. type: 'FROM_SIDE_PANEL_TO_GET_PAGE_INFO_CLEAN',
  43. },
  44. (response) => {
  45. if (chrome.runtime.lastError) {
  46. console.error('消息发送错误:', chrome.runtime.lastError, 555)
  47. rej(chrome.runtime.lastError)
  48. } else {
  49. res(response.data)
  50. }
  51. }
  52. )
  53. })
  54. }
  55. export function handleInput(xlsxData, formMap) {
  56. chrome.runtime.sendMessage({
  57. type: 'FROM_SIDE_PANEL_TO_INPUT_FORM',
  58. data: {
  59. excelData: xlsxData,
  60. formData: formMap
  61. }
  62. })
  63. }
  64. export function getXlsxValue(file) {
  65. return new Promise((res, rej) => {
  66. try {
  67. const reader = new FileReader()
  68. reader.readAsArrayBuffer(file)
  69. reader.onload = (e) => {
  70. const data = new Uint8Array(e.target.result)
  71. const workbook = XLSX.read(data, {
  72. type: 'array',
  73. cellDates: false,
  74. cellNF: true,
  75. cellText: true,
  76. dateNF: 'yyyy-mm-dd'
  77. })
  78. // 修复日期处理
  79. const firstSheet = workbook.Sheets[workbook.SheetNames[0]]
  80. // 转换为JSON数据
  81. const readData = XLSX.utils.sheet_to_json(firstSheet, {
  82. header: 1,
  83. raw: false,
  84. defval: '',
  85. dateNF: 'yyyy-mm-dd'
  86. })
  87. res(readData)
  88. }
  89. } catch (error) {
  90. rej()
  91. }
  92. })
  93. }
  94. export function downloadFile(file) {
  95. try {
  96. // 创建一个下载链接
  97. const downloadUrl = URL.createObjectURL(file);
  98. // 创建一个a标签用于下载
  99. const downloadLink = document.createElement('a');
  100. downloadLink.href = downloadUrl;
  101. downloadLink.download = file.name;
  102. // 添加到文档中并触发点击
  103. document.body.appendChild(downloadLink);
  104. downloadLink.click();
  105. // 清理
  106. document.body.removeChild(downloadLink);
  107. URL.revokeObjectURL(downloadUrl);
  108. ElMessage.success(`文件 ${file.name} 已下载到本地`);
  109. } catch (error) {
  110. console.error('下载文件失败:', error);
  111. ElMessage.error('下载文件失败');
  112. }
  113. }
  114. export function domToCanvas() {
  115. return new Promise((resolve, reject) => {
  116. // 检查是否已经存在 Shadow Host
  117. const existingHost = document.querySelector('[data-shadow-host="true"]')
  118. if (existingHost) {
  119. existingHost.remove()
  120. }
  121. const host = document.createElement('div')
  122. host.setAttribute('data-shadow-host', 'true') // 标记 Shadow Host
  123. document.body.appendChild(host)
  124. const shadowRoot = host.attachShadow({ mode: 'open' })
  125. // 创建遮罩层
  126. const overlay = document.createElement('div')
  127. overlay.id = 'overlay'
  128. overlay.style.position = 'fixed'
  129. overlay.style.top = '0'
  130. overlay.style.left = '0'
  131. overlay.style.width = '100%'
  132. overlay.style.height = '100%'
  133. overlay.style.backgroundColor = 'rgba(0, 0, 0, 0.5)'
  134. overlay.style.zIndex = '9999'
  135. overlay.style.cursor = 'crosshair'
  136. shadowRoot.appendChild(overlay)
  137. // 创建选择框
  138. const selectionBox = document.createElement('div')
  139. selectionBox.id = 'selection-box'
  140. selectionBox.style.position = 'absolute'
  141. selectionBox.style.border = '2px dashed #3498db'
  142. selectionBox.style.backgroundColor = 'rgba(52, 152, 219, 0.2)'
  143. selectionBox.style.pointerEvents = 'none'
  144. overlay.appendChild(selectionBox)
  145. let isSelecting = false
  146. let startX, startY, endX, endY
  147. // 鼠标按下事件
  148. overlay.addEventListener('mousedown', (e) => {
  149. isSelecting = true
  150. startX = e.clientX
  151. startY = e.clientY
  152. selectionBox.style.left = `${startX}px`
  153. selectionBox.style.top = `${startY}px`
  154. selectionBox.style.width = '0'
  155. selectionBox.style.height = '0'
  156. })
  157. // 鼠标移动事件
  158. overlay.addEventListener('mousemove', (e) => {
  159. if (isSelecting) {
  160. endX = e.clientX
  161. endY = e.clientY
  162. const width = Math.abs(endX - startX)
  163. const height = Math.abs(endY - startY)
  164. selectionBox.style.left = `${Math.min(startX, endX)}px`
  165. selectionBox.style.top = `${Math.min(startY, endY)}px`
  166. selectionBox.style.width = `${width}px`
  167. selectionBox.style.height = `${height}px`
  168. }
  169. })
  170. // 鼠标松开事件
  171. overlay.addEventListener('mouseup', async () => {
  172. isSelecting = false
  173. // 获取选择区域的坐标和尺寸
  174. const rect = {
  175. x: parseInt(selectionBox.style.left),
  176. y: parseInt(selectionBox.style.top),
  177. width: parseInt(selectionBox.style.width),
  178. height: parseInt(selectionBox.style.height)
  179. }
  180. console.log(rect)
  181. // 移除遮罩层和选择框
  182. overlay.remove()
  183. html2canvas(document.body, {
  184. x: rect.left,
  185. y: rect.top,
  186. width: rect.width,
  187. height: rect.height,
  188. backgroundColor: null, // 背景透明
  189. useCORS: true,
  190. allowTaint: true
  191. }).then(canvas => {
  192. // 直接转换为 base64
  193. const base64Data = canvas.toDataURL('image/png', 0.9); // 可调整质量参数
  194. resolve(base64Data);
  195. }).catch((error) => {
  196. reject(error)
  197. })
  198. })
  199. })
  200. }