Wie funktioniert das Einfügen von Bildern aus der Zwischenablage in Google Mail und Google Chrome 12+?

148

Ich habe einen Blog-Beitrag von Google gesehen , in dem die Möglichkeit erwähnt wird, Bilder direkt aus der Zwischenablage in eine Google Mail-Nachricht einzufügen, wenn Sie die neueste Version von Chrome verwenden. Ich habe dies mit meiner Version von Chrome (12.0.742.91 Beta-M) versucht und es funktioniert hervorragend mit Steuertasten oder dem Kontextmenü.

Aufgrund dieses Verhaltens muss ich davon ausgehen, dass die neueste Version des in Chrome verwendeten Webkits Bilder im Javascript-Einfügeereignis verarbeiten kann, aber ich konnte keine Verweise auf eine solche Verbesserung finden. Ich glaube, ZeroClipboard bindet an Tastendruckereignisse, um seine Flash-Funktionalität auszulösen, und funktioniert daher nicht über das Kontextmenü (außerdem ist ZeroClipboard browserübergreifend und der Beitrag besagt, dass dies nur mit Chrome funktioniert).

Wie funktioniert das und wo wurde das Webkit (oder Chrome) verbessert, das die Funktionalität aktiviert?

Emil Lerch
quelle
3
Es scheint, dass es auch zufällig mit Firefox funktioniert. Weiß jemand, ob dies mit Firefox unterstützt werden soll?
Sébastien

Antworten:

231

Ich habe einige Zeit damit verbracht, damit zu experimentieren. Es scheint der neuen API-Spezifikation für die Zwischenablage zu folgen . Sie können einen Ereignishandler zum Einfügen definieren, event.clipboardData.items anzeigen und getAsFile () aufrufen, um einen Blob abzurufen. Sobald Sie einen Blob haben, können Sie FileReader verwenden , um zu sehen, was darin enthalten ist. So können Sie eine Daten-URL für die Inhalte abrufen, die Sie gerade in Chrome eingefügt haben:

// window.addEventListener('paste', ... or
document.onpaste = function(event){
  var items = (event.clipboardData || event.originalEvent.clipboardData).items;
  console.log(JSON.stringify(items)); // will give you the mime types
  for (index in items) {
    var item = items[index];
    if (item.kind === 'file') {
      var blob = item.getAsFile();
      var reader = new FileReader();
      reader.onload = function(event){
        console.log(event.target.result)}; // data url!
      reader.readAsDataURL(blob);
    }
  }
}

Sobald Sie eine Daten-URL haben, können Sie das Bild auf der Seite anzeigen. Wenn Sie es stattdessen hochladen möchten, können Sie readAsBinaryString verwenden oder es mithilfe von FormData in eine XHR einfügen .

Nick Retallack
quelle
6
Hier an Strohhalmen festhalten, aber irgendwelche Ideen, warum event.clipboardData.items in Safari 5.1 'undefiniert' zu sein scheint? Oder sogar, wie man den Inhalt der Zwischenablage für eine Datei / einen Blob in Safari abruft? Funktioniert hervorragend in Chrome. Sie würden denken, Webkit wäre Webkit :(
Gavin Gilmour
7
@SenicaGonzalez, weil die Daten nur für die Dauer des Ereignisses vorhanden sind. Nach dem Ereignis ist es verschwunden. Wenn Sie also versuchen, das Objekt im Inspektor zu öffnen, sehen Sie nichts.
Nick Retallack
3
Ich führe dies auf Firefox und var blob = items [0] .getAsFile () throw TypeError: items is undefined
chinna_82
2
Würde es Ihnen etwas ausmachen, ein Beispiel für die Übermittlung einer XMLHttpRequest mit diesen Bilddaten zu erstellen? Das wäre echt schön: D
Poitroae
1
Hier ist, wie Sie das mit XMLHttpRequest einreichen können. Ich habe es in einem Blog geschrieben, nachdem ich es implementiert habe: blog.securevideo.com/2013/11/27/…
JT Taylor
56

Die Antwort von Nick scheint kleine Änderungen zu benötigen, um noch zu funktionieren :)

// window.addEventListener('paste', ... or
document.onpaste = function (event) {
  // use event.originalEvent.clipboard for newer chrome versions
  var items = (event.clipboardData  || event.originalEvent.clipboardData).items;
  console.log(JSON.stringify(items)); // will give you the mime types
  // find pasted image among pasted items
  var blob = null;
  for (var i = 0; i < items.length; i++) {
    if (items[i].type.indexOf("image") === 0) {
      blob = items[i].getAsFile();
    }
  }
  // load image if there is a pasted image
  if (blob !== null) {
    var reader = new FileReader();
    reader.onload = function(event) {
      console.log(event.target.result); // data url!
    };
    reader.readAsDataURL(blob);
  }
}

Beispiel für einen laufenden Code: http://jsfiddle.net/bt7BU/225/

Die Änderungen an Nicks Antwort waren also:

var items = event.clipboardData.items;

zu

var items = (event.clipboardData  || event.originalEvent.clipboardData).items;

Außerdem musste ich das zweite Element aus den eingefügten Elementen übernehmen (das erste scheint Text / HTML zu sein, wenn Sie ein Bild von einer anderen Webseite in den Puffer kopieren). Also habe ich mich verändert

  var blob = items[0].getAsFile();

zu einer Schleife, die den Gegenstand findet, der das Bild enthält (siehe oben)

Ich wusste nicht, wie ich direkt auf Nicks Antwort antworten sollte, hoffe es ist in Ordnung hier: $ :)

Robintibor
quelle
1
Wie sollen wir die Bilddaten als XMLHttpRequest senden?
Poitroae
Für andere, die dies lesen, kann die Antwort auf diese Frage jetzt dort enthalten sein: stackoverflow.com/questions/18055422/… :)
robintibor
4
Ich verstehe nicht. Wenn ich Dateien in den Browser einfüge, clipboardData.itemsist das in Google Chrome immer leer (Firefox funktioniert). Das Chrom muss jetzt fast genauso optimiert werden wie früher.
Tomáš Zato - Wiedereinsetzung Monica
1
Kleine Bearbeitung: if (blob! = Null) {(oder setze blob = null bei der Initialisierung)
Pancakeo
1
event.clipboardData.itemshat für mich auf dem neuesten Chrome gut funktioniert, nicht sicher, wann event.originalEvent...es nützlich ist?
Ruben Martinez Jr.
5

Webbrowser marschieren weiter vorwärts. Ich habe kürzlich Folgendes gefunden:

Code-Snippet - Zugriff auf Bilder aus der Zwischenablage mit Javascript

und das:

The Paste Wasteland (oder warum das onPaste-Ereignis ein Chaos ist)

Der erste Link beschreibt eine Möglichkeit, Zwischenablagebilder mit JavaScript nur unter Firefox und Chrome abzurufen. Der zweite Link enthält ein Postskriptum, in dem erwähnt wird, dass dieselbe Technik an den IE angepasst wurde (unbekannte Version).

Reiches Apodaca
quelle
Firefox aktiviert nicht einmal das Bearbeiten | Fügen Sie einen Menüpunkt für mich ein, damit ich nicht sehe, wie es in Firefox überhaupt funktioniert.
Podperson
Jeder dieser Links funktioniert zum Zeitpunkt des Kommentierens nicht.
Crazywako
2

Soweit ich weiss -

Mit HTML 5-Funktionen (Datei-API und zugehörige Funktionen) ist der Zugriff auf Bilddaten aus der Zwischenablage jetzt mit einfachem Javascript möglich.

Dies funktioniert jedoch nicht im IE (weniger als IE 10). Ich weiß auch nicht viel über die IE10-Unterstützung.

Für IE verwenden die Optionen, von denen ich glaube, dass sie die "Fallback" -Optionen sind, entweder die AIR-API von Adobe oder ein signiertes Applet

Saurshaz
quelle
1

Wow, das ist cool. Ich habe noch nicht in die Google Mail-Quelle eingetaucht, um dies herauszufinden (ich habe es mit der Drag-Out-Funktion getan), aber ich vermute, dass es sich um eine Erweiterung der Drag & Drop-API handelt, die Chrome bereits erweitert hat. Es gibt eine anständige Beschreibung der Funktionsweise der Drag-to-Desktop-Funktion: http://www.thecssninja.com/javascript/gmail-dragout , die Sie möglicherweise zumindest in die richtige Richtung weist.

Mark Kahn
quelle
0

Dies ist aus einem Beispiel mit Angular2-Typoskript, das für mein Projekt funktioniert. Hoffe es hilft jemandem. Die Logik ist auch in anderen Fällen dieselbe.

https://gist.github.com/sandeepsuvit/a8ba77faebba260455985504be24aef7

Hier ist eine Live-Implementierung:

https://stackblitz.com/edit/angular-f7kcny?file=app/app.component.ts

Sandeep K Nair
quelle
1
Könnten Sie bitte erklären, welchen Prozess Sie verfolgt haben? Sie können den Link https://stackblitz.com/edit/angular-f7kcny?file=app/app.component.tsin Chrome öffnen und dann mit der rechten Maustaste auf ein Bild von einer beliebigen Website klicken. Fügen Sie es dann in das dafür vorgesehene Textfeld ein. Es sollte so funktionieren.
Sandeep K Nair
aus dem Webbild kopiert funktioniert. Ich habe Bilder aus dem Windows Explorer ausprobiert, weshalb es damals nicht funktionierte. Kennen Sie zufällig eine Möglichkeit, das aus dem Windows Explorer kopierte Bild zu verarbeiten, um es auf einer Webseite einzufügen?
Battle Hawk
Ich habe diese Option noch nicht ausprobiert. Hoffentlich können Sie Erkenntnisse aus diesen Bibliotheken erhalten statt https://github.com/layerssss/paste.js/, https://github.com/JoelBesada/pasteboard. Unter diesen Links stehen Demos zur Verfügung, die Sie ausprobieren können.
Sandeep K Nair
event.clipboardData ist leer, wenn ich ein Image auf Windows-Betriebssystemcomputern eingefügt habe. Kann jemand erklären, warum dies passiert?
Tunç Doğan