Search code examples
javascriptexeccommand

JavaScript execCommand('copy') not working


I am unable to use the execCommand('copy'), trying to copy value which is selected in multi-select option. I am getting value in "temp" but the value which is getting in temp not copying or getting in clipboard.

{
        $propArr=array_unique($properties);
        echo "<div class='table-responsive'>";
            echo "<table class='bordered'>";
            foreach($propArr as $keyProp =>$val){
                echo "<tr>";
                    echo "<td>$val</td><td>";
                    echo "<select name='propval' id='propval' onclick='showpropval(this.value);' class='form-control' multiple>";
                    foreach($values as $k => $v){
                        if($val==$k){
                            foreach($v as $kv =>$fval){
                                echo "<option value='$fval'>$fval</option>";
                            }
                        }
                    }
                    echo "</select>";
                    echo"</td>";
                echo "</tr>";
            }
            echo "</table>";
        echo "</div>";
        }

<script>
        function showpropval(val)
        {
            var temp = val;
            temp.execCommand("copy");
            
        }
    </script>

Solution

  • I understand that your intention is the following: you want to copy the values of the selected options to the clipboard as soon as you select it.

    When you use document.execCommand('copy'), you copy whatever is selected on the page (such as content in a paragraph or in an input field itself).

    The catch is however that selecting options in <select> is not considered to be selected text. Worse yet, if you would like to trigger selecting text via javascript, there are some restrictions: you can only call .select() on an <input>or a <textarea> element.

    Here is what I would do: copy the selected options to a separate (not visible) input-field, select it and copy the content from that.

    Here is a fiddle that can serve as a demo: https://jsfiddle.net/Zomry/metcfvcq/13/

    I wil break it down here:

    First, add this element to the page. This is the input-field where we will copy the content from to the clipboard. Note that I have added tabindex -1 so you cannot reach it via tab key. I also included aria-hidden so screenreaders know it should ignore this.

    <input class='copyfrom' tabindex='-1' aria-hidden='true'>
    

    Then make the input field invisible by putting it off screen (did not work if I tried display: none; or other tricks)

    <style>
        .copyfrom {
            position: absolute;
            left: -9999px;
        }
    </style>
    

    Then copy the value to the input field, select it and copy it.

    var input = document.querySelector("input.copyfrom"); // select the input field
    
    function showpropval(val) {
        var selectedValues = getSelectValues(this); // get selected values
        input.value = test.join(','); // join them in a comma separated list
        input.select(); // select offscreen inputs text
        document.execCommand("copy"); // copy it
        this.focus(); // focus back on original, so we don't see any glitches
    } 
    
    // credits to: https://stackoverflow.com/questions/5866169/how-to-get-all-selected-values-of-a-multiple-select-box
    function getSelectValues(select) {
        var result = [];
        var options = select && select.options;
        var opt;
    
        for (var i=0, iLen=options.length; i<iLen; i++) {
            opt = options[i];
    
            if (opt.selected) {
              result.push(opt.value || opt.text);
            }
        }
      return result;
    }