我使用的是ReactJS,当用户点击一个链接时,我想复制一些文本到剪贴板。

我使用Chrome 52,我不需要支持任何其他浏览器。

我不明白为什么这段代码没有导致数据被复制到剪贴板。(代码片段的来源是Reddit的一篇帖子)。

我做错了吗?谁能建议有一个“正确”的方法来实现复制到剪贴板使用reactjs?

copyToClipboard = (text) => {
  console.log('text', text)
  var textField = document.createElement('textarea')
  textField.innerText = text
  document.body.appendChild(textField)
  textField.select()
  document.execCommand('copy')
  textField.remove()
}

当前回答

无需安装第三方软件包。我尽量让它简单。这对我来说很有效。

import React, { useState } from "react"    
function MyApp() {
    const [copySuccess, setCopySuccess] = useState(null);
    const copyToClipBoard = async copyMe => {
       try {
           await navigator.clipboard.writeText(copyMe);
           setCopySuccess('Copied!');
       } 
       catch (err) {
           setCopySuccess('Failed to copy!');
       }
    };
     
    return (
        <button onClick={(e) => copyToClipBoard(what you want to copy goes here)} >
           My button
        </button>    
       )
    }

其他回答

使用材质UI完全工作的React组件

为了更好地理解,我还准备了一个CodeSandbox。希望这能有所帮助。

import { useState } from "react";
import { IconButton, Snackbar } from "@mui/material";
import ShareIcon from "@mui/icons-material/Share";

const CopyToClipboardButton = () => {
  const [open, setOpen] = useState(false);

  const handleClick = () => {
    setOpen(true);
    navigator.clipboard.writeText(window.location.toString());
  };

  return (
    <>
      <IconButton onClick={handleClick} color="primary">
        <ShareIcon />
      </IconButton>
      <Snackbar
        message="Copied to clibboard"
        anchorOrigin={{ vertical: "top", horizontal: "center" }}
        autoHideDuration={20000}
        onClose={() => setOpen(false)}
        open={open}
      />
    </>
  );
};

export default CopyToClipboardButton;

下面是按钮的样子:

当你点击它时:

来源:https://fwuensche.medium.com/react——按钮——复制到剪贴板- 75 ef5ecdc708

最简单的方法是使用react-copy-to-clipboard npm包。

您可以使用以下命令安装它

npm install --save react react-copy-to-clipboard

请按照以下方式使用它。

const App = React.createClass({
  getInitialState() {
    return {value: '', copied: false};
  },


  onChange({target: {value}}) {
    this.setState({value, copied: false});
  },


  onCopy() {
    this.setState({copied: true});
  },


  render() {
    return (
      <div>

          <input value={this.state.value} size={10} onChange={this.onChange} />

        <CopyToClipboard text={this.state.value} onCopy={this.onCopy}>
          <button>Copy</button>
        </CopyToClipboard>

                <div>
        {this.state.copied ? <span >Copied.</span> : null}
                </div>
        <br />

        <input type="text" />

      </div>
    );
  }
});

ReactDOM.render(<App />, document.getElementById('container'));

以下链接提供了详细的解释

https://www.npmjs.com/package/react-copy-to-clipboard

这是一把移动小提琴。

对于那些试图从DIV而不是文本字段中进行选择的人,下面是代码。代码是不言自明的,但如果你想了解更多信息,请在这里评论:

     import React from 'react';
     ....

    //set ref to your div
          setRef = (ref) => {
            // debugger; //eslint-disable-line
            this.dialogRef = ref;
          };

          createMarkeup = content => ({
            __html: content,
          });

    //following function select and copy data to the clipboard from the selected Div. 
   //Please note that it is only tested in chrome but compatibility for other browsers can be easily done

          copyDataToClipboard = () => {
            try {
              const range = document.createRange();
              const selection = window.getSelection();
              range.selectNodeContents(this.dialogRef);
              selection.removeAllRanges();
              selection.addRange(range);
              document.execCommand('copy');
              this.showNotification('Macro copied successfully.', 'info');
              this.props.closeMacroWindow();
            } catch (err) {
              // console.log(err); //eslint-disable-line
              //alert('Macro copy failed.');
            }
          };

              render() {
                    return (
                        <div
                          id="macroDiv"
                          ref={(el) => {
                            this.dialogRef = el;
                          }}
                          // className={classes.paper}
                          dangerouslySetInnerHTML={this.createMarkeup(this.props.content)}
                        />
                    );
            }

你可以做到这一点,而不需要一个外部库,例如:在一个按钮

<button 
  onClick={() =>  navigator.clipboard.writeText('Copy this text to clipboard')}
>
  Copy
</button>

对于ie11和更老的浏览器,你可能需要稍微改变一下代码,这里有一个例子:

<button 
  onClick={() =>  window.clipboardData.setData("Text", 'Copy this text to clipboard')}>
 Copy
</button>

您可以使用useRef选择元素中的文本,然后将其复制到剪贴板

import React, { useRef } from "react";

const Comp = () => {
   const copyTxt = useRef();

   const handleCopyTxt = () => {
   let txtDiv = copyTxt.current;
      if (document.selection) {
        // IE
        var range = document.body.createTextRange();
        range.moveToElementText(txtDiv);
        range.select();
      } else if (window.getSelection) {
        // other browsers
        var range = document.createRange();
        range.selectNode(txtDiv);
        window.getSelection().removeAllRanges();
        window.getSelection().addRange(range);
      }
      document.execCommand("copy");
    }

    return ( <div ref={copyTxt} > some text to copied </div> )
}