Greasy Fork 还支持 简体中文。

paste to form file field

ctrl-v to paste clipboard file into file form field

目前為 2021-08-26 提交的版本,檢視 最新版本

  1. // ==UserScript==
  2. // @name paste to form file field
  3. // @namespace http://gholk.github.io
  4. // @description ctrl-v to paste clipboard file into file form field
  5. // @match https://www.google.com/imghp
  6. // @version 4.1.0
  7. // @grant GM.xmlHttpRequest
  8. // @license GPLv3
  9. // ==/UserScript==
  10.  
  11. document.body.addEventListener('paste', (paste) => {
  12. if (paste.clipboardData.files.length == 0) return
  13. putFileIntoForm(paste.clipboardData.files)
  14. })
  15. document.body.addEventListener('dragover', (over) => over.preventDefault())
  16. document.body.addEventListener('drop', async (drop) => {
  17. drop.preventDefault()
  18. const data = drop.dataTransfer
  19. console.debug('type', ...data.types)
  20. let fileList
  21. if (typeof GM != 'undefined' &&
  22. data.files.length == 0 && ~data.types.indexOf('text/plain')) {
  23. const urlList = data.getData('text/plain')
  24. .split('\n').filter(u => u.charAt(0) != '#')
  25. console.debug(urlList)
  26. try {
  27. fileList = await Promise.all(urlList.map(fetchFile))
  28. console.debug(fileList)
  29. fileList = createFileList(...fileList)
  30. }
  31. catch (e) {
  32. console.error(e)
  33. return
  34. }
  35. }
  36. else fileList = drop.dataTransfer.files
  37. putFileIntoForm(fileList)
  38. })
  39.  
  40. function createFileList(...fileList) {
  41. // attribute to https://stackoverflow.com/a/56447852/8362703
  42. const data = new DataTransfer()
  43. for (const file of fileList) data.items.add(file)
  44. return data.files
  45. }
  46.  
  47. async function fetchFile(url) {
  48. function xhrToFileType(xhr) {
  49. for (const row of xhr.responseHeaders.split(/\n/)) {
  50. // line-end with \r\n
  51. const scan = row.match(/^content-type: (.*)\/(.*)/i)
  52. if (scan) return scan[2]
  53. }
  54. }
  55. return await new Promise((resolve, reject) => {
  56. GM.xmlHttpRequest({
  57. method: 'GET', url,
  58. responseType: 'blob',
  59. onload(xhr) {
  60. const blob = xhr.response
  61. const type = xhrToFileType(xhr)
  62. let file
  63. if (type) {
  64. file = new File(
  65. [blob], `drop-image.${type}`,
  66. {type: `image/${type}`}
  67. )
  68. }
  69. else file = new File([blob], `drop-image`)
  70. resolve(file)
  71. },
  72. onerror(xhr) {
  73. reject(xhr.statusText)
  74. }
  75. })
  76. })
  77. }
  78.  
  79. function putFileIntoForm(fileList) {
  80. const input = document.querySelector('input[type = "file"]')
  81. if (!input) return
  82. console.debug('fileList:', ...fileList)
  83. // attribute to https://stackoverflow.com/a/50427897/8362703
  84. input.files = fileList
  85. const change = new Event('change', {bubbles: true, cancelable: false})
  86. input.dispatchEvent(change)
  87. }