24

On my site users can paste text (in this case a url) into an input field. I'd like to capture the value of the text that was pasted using jQuery. I've got this to work in FF using the code below, but it doesn't work in IE (I don't think IE supports the "paste" event).

Anyone know how to make this work across all modern browsers? I've found a few other answers to this on SO but most are FF-only and none seemed to offer a complete solution.

Here's the code I have so far:

$("input.url").live('paste', function(event) {
    var _this = this;
    // Short pause to wait for paste to complete
    setTimeout( function() {
        var text = $(_this).val();
        $(".display").html(text);
    }, 100);
});

JSFiddle: http://jsfiddle.net/TZWsB/1/

Lightness Races in Orbit
  • 358,771
  • 68
  • 593
  • 989
rolling stone
  • 11,148
  • 9
  • 40
  • 60
  • 2
    http://stackoverflow.com/questions/2176861/javascript-get-clipboard-data-on-paste-event-cross-browser/2177059#2177059 - similar – Avien Aug 01 '11 at 18:08
  • thanks @Avien, wow that is some complicated hack :) unfortunately reading through the solutions none of them work 100% correctly, or work across all modern browsers. – rolling stone Aug 01 '11 at 18:17
  • This one might help too, uses jquery and is a lot simpler: http://stackoverflow.com/questions/2903991/how-to-detect-ctrlv-ctrlc-using-javascript – Sitnik Aug 01 '11 at 18:18

5 Answers5

29

jQuery has a problem with the live-method with the paste-event in the IE; workaround:

$(document).ready(function() {
    $(".url").bind('paste', function(event) {
        var _this = this;
        // Short pause to wait for paste to complete
        setTimeout( function() {
            var text = $(_this).val();
            $(".display").html(text);
        }, 100);
    });
});

Fiddle: http://jsfiddle.net/Trg9F/

scessor
  • 15,775
  • 4
  • 39
  • 53
  • +1 thanks @scessor, that is very helpful to know. the problem is that i let users dynamically add more inputs, so i need the live method. is there a way to make this work with live other than hacking together a solution involving hidden inputs? – rolling stone Aug 01 '11 at 18:36
  • I have a solution without live: when you add the inputs dynamically, you can unbind all nodes with the class url, and bind the paste-event again; not very nice, but simple. – scessor Aug 01 '11 at 18:41
  • There's 2016 and Chrome has the same problem as well. I was wondering for a couple of minutes what I did wrong till I found this post. thanks for your answer, it's helpful a lot! – Paweł Dec 12 '16 at 18:33
  • This is answer also true for regular javascript – ganjeii Jan 23 '18 at 20:41
24
$('input').on('paste', function(e) {
    // common browser -> e.originalEvent.clipboardData
    // uncommon browser -> window.clipboardData
    var clipboardData = e.clipboardData || e.originalEvent.clipboardData || window.clipboardData;
    var pastedData = clipboardData.getData('text');
});
Sakamoto Riku
  • 249
  • 2
  • 2
19

Listen for the change event as well as paste. change will reliably fire on a changed field before submission, whereas paste only happens on browsers that support it on an explicit paste; it won't be triggered by other editing actions such as drag-and-drop, cut-copy, undo-redo, spellcheck, IME substitution etc.

The problem with change is that it doesn't fire straight away, only when editing in a field is finished. If you want to catch all changes as they happen, the event would be input... except that this is a new HTML5 feature that isn't supported everywhere (notably: IE<9). You could nearly do it by catching all these events:

$('.url').bind('input change paste keyup mouseup',function(e){
    ...
});

But if you want to definitely catch every change quickly on browsers that don't support input, you have no choice but to poll the value on a setInterval.

bobince
  • 498,320
  • 101
  • 621
  • 807
  • +1 thanks @bobince! i should probably mention that all users will be doing (well, i should say should be doing) in this input field is pasting in a url. also it looks like i'm wrong and IE does support 'paste', it just has some problems with 'live' and 'paste'. my problem is that i'm dynamically generating some content based on the url they paste that i'd like to display to the user to make sure it's correct before they submit. in fact i'm actually disabling the submit button when a url is pasted until the jQuery function that does all that is complete. Any advice would be much appreciated! – rolling stone Aug 01 '11 at 18:48
  • Yes, `onpaste` doesn't bubble in some situations in IE, and jQuery's `live` uses event delegation, which requires bubbling. There are also other browser-specific issues, such as onpaste not firing in textareas in Safari. Regardless of compatibility issues, I would advise allowing a field to be filled in in any way the user chooses—including direct typing and drag-and-drop—rather than specifically targeting only paste operations. – bobince Aug 02 '11 at 17:39
  • thanks @bobince, will definitely factor that in. is `change` the best event to capture drag-and-drop? – rolling stone Aug 02 '11 at 17:49
  • @bobince, thanks, 'input' event is not available in IE8. I found 'drop' event helpful. It is working on IE8/9/10, Chrome, FF. – bob Jul 04 '13 at 22:19
4

Even better is it to use e.originalEvent.clipboardData.getData('text'); to retrieve pasted data;

$("input").on("paste", function(e) { 
    var pastedData = e.originalEvent.clipboardData.getData('text');
    // ... now do with pastedData whatever you like ...
});

This way you can avoid timeouts and it is supported on all major browsers.

Triple S
  • 66
  • 2
  • I like this idea but for me, e.originalEvent has many attributes but it has no clipboardData field/attribute :( [FYI I am using Microsoft TypeSafe & JQuery 3.1.1 & jQuery UI 1.12.1 to write my Javascript.] – Zeek2 Feb 22 '17 at 13:01
0

Maybe try using the onblur event instead. So the user c/p into the input and when they leave the field the script checks what's there. This could save a whole lot of hassle, since it works for mouse and key c/p as well as manually entered input.

qw3n
  • 5,558
  • 4
  • 28
  • 58
  • thanks @qw3n. the problem is that there's only the url field on the page, so i'm sure there will be instances when the user just pastes in the url and hits submit (without leaving the field). – rolling stone Aug 01 '11 at 18:13
  • @rolling stone Ok well you could do a two pronged check. Get the `onsubmit` event and check the input. If empty return true else return false. The problem is you will have to do something to prevent the function from running twice. Since the `onblur` event will still fire. Maybe have boolean toggle variable for when you have fired the event from one function. Hope this makes sense. It is a complicated, but I think less so then the alternative. – qw3n Aug 01 '11 at 18:15