问题
There are two ways to copy an image through the browser (for example chrome), the copy image and the copy address of the image.
When I copy the image address and paste it using my paste Image button, I can get the image copied from the base64 browser. But when I copy the image, I can't get the image. Is there a way to obtain the image using the image coipar, as shown in the examples?
Demo
code
clickPaste() {
let self = this;
(navigator as any).clipboard.readText().then(clipboard => self.clip = clipboard);
console.log(self.clip) // copy image adress ---> base64
}
Example copy image address - working
Example copy image - does not work
I know that copying the image and copying the image's address are different things, but I couldn't find out how I can get the image (blob or base64) when I use copy the image.
回答1:
You can access it from the paste ClipboardEvent's .clipboardData DataTransfer.
It will be in the .files
FileList if available:
document.onpaste = (evt) => {
const dT = evt.clipboardData || window.clipboardData;
const file = dT.files[ 0 ];
console.log( file );
};
img{ height: 100vh; }
<div contenteditable>You can paste the image here</div>
<figure>
<figcaption>Copy this image</figcaption>
<img src="https://upload.wikimedia.org/wikipedia/commons/4/47/PNG_transparency_demonstration_1.png">
</figure>
If you need to get it outside of such an event, then you will need to use the asynchronous Clipboard API.
Unfortunately, this API is not yet very well supported (currently Blink only), but anyway, here is how you can read an image file using this API.
You first need to request / check for the "clipboard-read"
Permission.
Then if the request has not be denied, you can try to read the whole content of the clipboard by calling navigator.clipboard.read()
. This will return a DataTransferItemsList (technically an Array), from which you will still have to pick the one that holds the .type
you want to access.
In your case you only know it's an image, but there are several types available for images, so you need to determine which one it is while doing this check.
document.getElementById('btn').onclick = async (evt) => {
const auth = await navigator.permissions.query( { name: "clipboard-read" } );
if( auth.state !== 'denied' ) {
const item_list = await navigator.clipboard.read();
let image_type; // we will feed this later
const item = item_list.find( item => // choose the one item holding our image
item.types.some( type => { // does this item have our type
if( type.startsWith( 'image/' ) ) {
image_type = type; // store which kind of image type it is
return true;
}
} )
);
const file = item && await item.getType( image_type );
console.log( file );
}
};
img{ height: 100vh; }
<button id="btn">read clipboard content</button>
<figure>
<figcaption>Copy this image</figcaption>
<img src="https://upload.wikimedia.org/wikipedia/commons/4/47/PNG_transparency_demonstration_1.png">
</figure>
回答2:
This is an example from this tutorial: First you add an event listener for "paste":
window.addEventListener("paste", function(e){
// Handle the event
retrieveImageFromClipboardAsBase64(e, function(imageDataBase64){
// If there's an image, open it in the browser as a new window :)
if(imageDataBase64){
// data:image/png;base64,iVBORw0KGgoAAAAN......
window.open(imageDataBase64);
}
});
}, false);
And using this funcion you can retrieve the image as base64:
**
* This handler retrieves the images from the clipboard as a base64 string and returns it in a callback.
*
* @param pasteEvent
* @param callback
*/
function retrieveImageFromClipboardAsBase64(pasteEvent, callback, imageFormat){
if(pasteEvent.clipboardData == false){
if(typeof(callback) == "function"){
callback(undefined);
}
};
// retrive elements from clipboard
var items = pasteEvent.clipboardData.items;
if(items == undefined){
if(typeof(callback) == "function"){
callback(undefined);
}
};
// loop the elements
for (var i = 0; i < items.length; i++) {
// Skip content if not image
if (items[i].type.indexOf("image") == -1) continue;
// Retrieve image on clipboard as blob
var blob = items[i].getAsFile();
// Create an abstract canvas and get context
var mycanvas = document.createElement("canvas");
var ctx = mycanvas.getContext('2d');
// Create an image
var img = new Image();
// Once the image loads, render the img on the canvas
img.onload = function(){
// Update dimensions of the canvas with the dimensions of the image
mycanvas.width = this.width;
mycanvas.height = this.height;
// Draw the image
ctx.drawImage(img, 0, 0);
// Execute callback with the base64 URI of the image
if(typeof(callback) == "function"){
callback(mycanvas.toDataURL(
(imageFormat || "image/png")
));
}
};
// Crossbrowser support for URL
var URLObj = window.URL || window.webkitURL;
// Creates a DOMString containing a URL representing the object given in the parameter
// namely the original Blob
img.src = URLObj.createObjectURL(blob);
}
}
来源:https://stackoverflow.com/questions/60503912/get-image-using-paste-from-the-browser