- // ==UserScript==
- // @name Drag-Drop Image Uploader
- // @namespace http://tampermonkey.net/
- // @version 0.2.1
- // @description Enables image uploading by simply dragging and dropping images onto a fixed div in the bottom right corner of the page. Easily upload and use images on any website with this convenient script.
- // @match https://*/*
- // @grant none
- // @license MIT License
- // @author CY Fung
- // @icon https://raw.githubusercontent.com/cyfung1031/userscript-supports/main/icons/drag-drop-image-uploader.svg
- // @run-at document-start
- // ==/UserScript==
-
- (function () {
- 'use strict';
-
- if (location.hostname === 'lihkg.com') {
-
- if (location.pathname !== '/robots.txt') return;
- if (window.name !== 'pNwjxjQi') return;
- if (window === top) return;
-
-
- function T(e) {
- return new Promise(function (resolve, reject) {
- window.history.replaceState(null, '', 'https://lihkg.com');
- let formData = new FormData();
- formData.append('image', e);
-
- fetch('https://api.na.cx/upload', {
- method: 'POST',
- body: formData,
-
- "mode": "cors",
- "credentials": "omit",
-
- referrerPolicy: "no-referrer",
- cache: "default", // no effect on POST request
- // cache: "force-cache",
- redirect: "error", // there shall be no redirection in this API request
- integrity: "",
- keepalive: false,
-
- "headers": {
- "Accept-Encoding": "gzip, deflate, br",
- "Accept": "application/json",
- },
-
- })
- .then(function (response) {
- if (response.ok) {
- return response.json();
- } else {
- throw new Error('Status is not 200');
- }
- })
- .then(function (response) {
- let status = response.status;
- let url = response.url;
- let error = response.error;
-
- if (status === 200) {
- resolve(url);
- } else {
- reject(new Error(error));
- }
- })
- .catch(function (error) {
- reject(error);
- });
- });
- }
-
-
- let iframe = document;
-
- // Function to handle the dragenter event
- function handleDragEnter(e) {
- top.postMessage('pNwjxjQi-top-dragenter', '*');
- // Add a class to visually indicate the drag over the iframe
- //iframe.classList.add("drag-over");
- }
-
- // Function to handle the dragover event
- function handleDragOver(e) {
- // top.postMessage('pNwjxjQi-top-dragover','*');
- e.preventDefault();
- e.dataTransfer.dropEffect = 'copy';
- }
-
- // Function to handle the dragleave event
- function handleDragLeave(e) {
- top.postMessage('pNwjxjQi-top-dragleave', '*');
- // Remove the class when the drag leaves the iframe
- //iframe.classList.remove("drag-over");
- }
-
- async function goUpload(e) {
-
- let files = e.dataTransfer.files;
- let images = [...files].filter(file => file.type == "image/png" || file.type == "image/jpg" || file.type == "image/jpeg" || file.type == "image/gif")
- // console.log(images);
-
- for (const image of images) {
- await T(image)
- .then(function (url) {
- // focusElement.focus();
- // document.execCommand("insertText", false, url)
- top.postMessage({ p: 'pNwjxjQi-top-finish-upload', url: url }, '*')
- console.log('Uploaded image URL:', url);
- })
- .catch(function (error) {
- console.error('Upload failed:', error);
- });
- }
-
- }
-
- // Function to handle the drop event
- function handleDrop(e) {
- e.preventDefault();
- top.postMessage('pNwjxjQi-top-drop', '*');
-
- // Remove the class when the drop occurs
- //iframe.classList.remove("drag-over");
-
- // Access the dropped files or data
-
- goUpload(e);
-
- // Process the dropped files or data as needed
- // ...
- }
- // Add event listeners for drag and drop events
- iframe.addEventListener("dragenter", handleDragEnter, false);
- iframe.addEventListener("dragover", handleDragOver, false);
- iframe.addEventListener("dragleave", handleDragLeave, false);
- iframe.addEventListener("drop", handleDrop, false);
-
-
- top.postMessage('pNwjxjQi-top-uploader-ready', '*');
-
-
- } else {
-
- function onReady() {
-
- let fixedDiv = null;
-
- let focusElement = null;
-
- let moused = false;
-
- let lastDragIn = 0;
- let cid = 0;
-
-
- function createFixedDiv() {
-
-
- // Create the fixed div element
- let fixedDiv = document.createElement('div');
- fixedDiv.style.position = 'fixed';
- fixedDiv.style.zIndex = '8888';
- fixedDiv.style.bottom = '10px';
- fixedDiv.style.right = '10px';
- fixedDiv.style.width = '200px';
- fixedDiv.style.height = '200px';
- // fixedDiv.style.backgroundColor = 'rgba(0, 0, 0, 0.5)';
- fixedDiv.style.border = '2px solid rgb(244, 244, 244)';
- fixedDiv.style.outline = '2px solid rgb(20, 20, 20)';
- fixedDiv.style.borderRadius = '5px';
- fixedDiv.style.padding = '0px';
- fixedDiv.style.color = 'white';
- fixedDiv.style.fontSize = '14px';
- fixedDiv.style.textAlign = 'center';
- // fixedDiv.style.cursor = 'move';
- // fixedDiv.draggable = true;
- fixedDiv.style.opacity = '0'; // Set initial opacity to 0 (hidden)
- fixedDiv.style.display = 'none';
- fixedDiv.id = 'ewIMf5Dw';
-
- fixedDiv.style.background = 'url(https://raw.githubusercontent.com/cyfung1031/userscript-supports/main/icons/drag-drop-image-uploader.svg)';
- fixedDiv.style.background = 'url(https://raw.githubusercontent.com/cyfung1031/userscript-supports/main/icons/drag-drop-image-uploader.svg), rgba(135,206,250, 0.2)';
-
- fixedDiv.style.backgroundPosition = 'center';
- fixedDiv.style.backgroundSize = 'cover';
- fixedDiv.style.backgroundRepeat = 'no-repeat';
-
- fixedDiv.style.pointerEvents = 'none';
-
- // Append the div to the document body
- document.body.appendChild(fixedDiv);
-
- // Create the Intersection Observer
- let observer = new IntersectionObserver(function (entries) {
- entries.forEach(function (entry) {
- if (entry.isIntersecting) {
- // When fixedDiv appears, check if it has an iframe inside
- let iframe = fixedDiv.querySelector('iframe');
- if (!iframe) {
- // If no iframe inside, create and append one
- iframe = document.createElement('iframe');
- setupIframe(iframe);
- iframe.src = 'https://lihkg.com/robots.txt';
- fixedDiv.appendChild(iframe);
- }
- }
- });
- });
-
- // Observe the fixedDiv element
- observer.observe(fixedDiv);
-
- return fixedDiv;
- }
- function setupIframe(iframe) {
- if (!fixedDiv) return;
- iframe.name = 'pNwjxjQi';
-
- iframe.style.position = 'relative';
- iframe.style.width = '100%';
- iframe.style.height = '100%';
- iframe.style.opacity = '0';
- iframe.style.pointerEvents = 'all';
- iframe.style.transform = 'translateY(-300vh)';
- fixedDiv.style.transform = 'translateY(-300vh)';
-
- }
-
-
-
-
- document.addEventListener('dragleave', function (event) {
- if (!fixedDiv) return;
- if (moused) return;
-
- if (cid > 0) cid = clearTimeout(cid);
- if (event.relatedTarget) return;
- // console.log(221);
-
- let endTime = Date.now();
- cid = setTimeout(() => {
- cid = 0;
- requestAnimationFrame(() => {
- if (lastDragIn > endTime) return;
-
- if (fixedDiv.style.display !== 'none' && !moused) {
-
- // focusElement = null;
- fixedDiv.style.display = 'none';
- fixedDiv.style.opacity = '0';
- }
- });
- }, 80)
-
- event.preventDefault();
-
- });
-
- document.addEventListener('dragenter', function (event) {
- if (!fixedDiv) fixedDiv = createFixedDiv();
- if (moused) return;
- if (cid > 0) cid = clearTimeout(cid);
- if (event.relatedTarget) return;
- // console.log(222);
-
-
- lastDragIn = Date.now();
-
- let activeNode = document.activeElement || 0;
- let activeNodeName = activeNode.nodeName;
- if (activeNodeName === 'TEXTAREA' || (activeNodeName === 'INPUT' && (!activeNode.type || activeNode.type == 'text'))) {
- if (fixedDiv.style.display === 'none') {
- fixedDiv.style.display = 'block';
- fixedDiv.style.opacity = '0.4';
- focusElement = activeNode;
- // console.log(focusElement)
- }
- }
-
- requestAnimationFrame(() => {
-
- lastDragIn = Date.now();
- });
- }, true);
-
- document.addEventListener('drop', function (event) {
- if (!fixedDiv) return;
- moused = false;
- if (moused) return;
- if (cid > 0) cid = clearTimeout(cid);
- // console.log(223);
-
- let endTime = Date.now();
- cid = setTimeout(() => {
- cid = 0;
- if (lastDragIn > endTime) return;
- if (fixedDiv.style.display !== 'none' && !moused) {
- // focusElement = null;
-
- fixedDiv.style.display = 'none';
- fixedDiv.style.opacity = '0';
- }
- }, 80)
-
-
- }, true);
-
-
-
- window.addEventListener('message', event => {
- if (!fixedDiv) return;
-
- let data = (((event || 0).data || 0));
-
-
- if (data === 'pNwjxjQi-top-uploader-ready') {
-
- let fixedDiv = document.querySelector('#ewIMf5Dw');
- let iframe = fixedDiv.querySelector('iframe');
-
- iframe.style.transform = '';
- fixedDiv.style.transform = '';
-
- }
-
- if (data === 'pNwjxjQi-top-dragenter') {
- moused = true;
- fixedDiv.style.opacity = '1';
- }
- if (data === 'pNwjxjQi-top-dragleave') {
- moused = false;
- fixedDiv.style.opacity = '0.4';
- }
-
- if (data === 'pNwjxjQi-top-dragenter') {
-
- if (cid > 0) cid = clearTimeout(cid);
- }
-
- if (data === 'pNwjxjQi-top-dragleave') {
-
- let endTime = Date.now();
- if (cid > 0) cid = clearTimeout(cid);
- cid = setTimeout(() => {
- cid = 0;
- requestAnimationFrame(() => {
- if (lastDragIn > endTime) return;
-
- if (fixedDiv.style.display !== 'none' && !moused) {
-
- // focusElement = null;
- fixedDiv.style.display = 'none';
- fixedDiv.style.opacity = '0';
- }
- });
- }, 80)
-
- }
-
- if (data.p === 'pNwjxjQi-top-finish-upload') {
- let url = event.data.url;
- focusElement.focus();
- document.execCommand("insertText", false, url)
- }
-
- if (data === 'pNwjxjQi-top-drop') {
- moused = false;
-
- let endTime = Date.now();
- cid = setTimeout(() => {
- cid = 0;
- if (lastDragIn > endTime) return;
- if (fixedDiv.style.display !== 'none' && !moused) {
- // focusElement = null;
-
- fixedDiv.style.display = 'none';
- fixedDiv.style.opacity = '0';
- }
- }, 80)
- }
-
- })
-
- }
- if (document.readyState !== 'loading') {
- onReady();
- } else {
- document.addEventListener('DOMContentLoaded', onReady, false);
- }
-
-
-
- }
- })();