4

I'd like to copy the content of this for-loop into clipboard:

<div ref="text" class="links">
        <div class="row" v-for="(name, index) in resultNames" :key="index" >                                    
            <p>{{makeUrl(name)}} </p>
        </div>   
</div>  
<button   @click="handleCopy">Copy to Clipboard</button> 

I followed this answer and came up with this method:

  handleCopy() {
     this.$refs.text.select();
     document.execCommand('copy');
    }

But this results in:

Uncaught TypeError: this.$refs.text.select is not a function

So I'm left clueless how can I solve this withouth using third party javascript plugins?

P.S. I tried some JS specific suggested answers, like this, but get error:

Uncaught TypeError: Failed to execute 'selectNode' on 'Range': parameter 1 is not of type 'Node'.
qliq
  • 11,695
  • 15
  • 54
  • 66
  • You can simply mirror the data in a hidden ` –  Jan 14 '19 at 09:49
  • You need to take the `innerHTML` and put it inside a `textarea` and only then select and copy it. – Oram Jan 14 '19 at 09:50
  • @ChrisG how can I do that? – qliq Jan 14 '19 at 09:50
  • Possible duplicate of [How do I copy to the clipboard in JavaScript?](https://stackoverflow.com/questions/400212/how-do-i-copy-to-the-clipboard-in-javascript) More specifically - [this answer](https://stackoverflow.com/a/30810322/9839191) – Oram Jan 14 '19 at 09:51
  • @ChrisG That answer does not work in Vue.js. I tried and failed: `Uncaught TypeError: Failed to execute 'selectNode' on 'Range': parameter 1 is not of type 'Node'.` – qliq Jan 14 '19 at 10:04
  • 1
    Works fine for me: https://codesandbox.io/s/484yxqpmm4 –  Jan 14 '19 at 10:21

3 Answers3

10

Based on this answer, here's a function to select an HTMLElement's text:

selectText(element) {
  var range;
  if (document.selection) {
    // IE
    range = document.body.createTextRange();
    range.moveToElementText(element);
    range.select();
  } else if (window.getSelection) {
    range = document.createRange();
    range.selectNode(element);
    window.getSelection().removeAllRanges();
    window.getSelection().addRange(range);
  }
}

What's left to do is to a) pass the element b) call the copy command:

this.selectText(this.$refs.text); // e.g. <div ref="text">
document.execCommand("copy");
  • 1
    it's not working - error message appeared: Error in v-on handler: "TypeError: Failed to execute 'selectNode' on 'Range': parameter 1 is not of type 'Node'." when I put div's ref as parameter. – Schroet Feb 24 '20 at 17:02
  • @Schroet make sure that your div contains only the text to copy in my case i used this to copy a phone number : {{ phone_icon.phone }} – Amdouni Mohamed Ali Dec 20 '20 at 17:35
3

You can make use of the vue plugin on npm:vue-clipboard

Lets first make the html data which you want to be copied. After that we can make use of the npm plugin to copy the html data

new Vue({
    el: '#app',
    data: {
        HTMLcontent:'',
        resultNames:["John","Steward","Rock"]
    },
    created() {
    },
    methods:{
        makeData(){
            var self = this;
            for(var i = 0; i < self.resultNames.length; i++){
                self.HTMLcontent += '<p>'+self.resultNames[i]+'</p>';
            }
        },
        copyData(){
            this.makeData();
            console.log(this.HTMLcontent);
        }
    }
});

After that install a vue-plugin

npm install --save v-clipboard
import Clipboard from 'v-clipboard'
Vue.use(Clipboard)

After that make change to the copyData function as below

copyData(){
    this.makeData();
    this.$clipboard(this.invite_code);
    alert("Copied to clipboard");
}

Hope that solves your query

Ankush Sood
  • 412
  • 3
  • 13
1

Had the same issue, but vue clipboard and clipboard2, didn't help me

In result for copy to clipbboard I used JQuery and vue events

HTML part

<div class="input-group">
  <input type="text" class="form-control copyLinkInput" :value="link">
  <div class="input-group-append" @click="doCopy">
    <div class="input-group-text">
      <i class="fas fa-copy"></i>
    </div>
  </div>
</div>

Vue.js part

...

props: ['link'],
methods: {
  doCopy: function (e) {
    let selectEl = $(e.target).parents('.input-group').find('.copyLinkInput')[0];

    selectEl.select();
    document.execCommand("copy");
  }
}

...
Alex Pilyavskiy
  • 140
  • 1
  • 3