React TypeScript select 来自 ref 的节点内容

React TypeScript select node contents from a ref

我有没有可能将 React ref 提供给文档范围 .selectNodeContents() 函数。我最终遇到的错误是:

Argument of type 'HTMLDivElement | null' is not assignable to parameter of type 'Node'.
  Type 'null' is not assignable to type 'Node'.ts(2345)
(property) React.RefObject<HTMLDivElement>.current: HTMLDivElement | null

我的假设是 ref 在实际分配之前声明,但我真的不明白如何在 TypeScript 中克服这个问题。如有重复请见谅,只是网上没找到

export const Code: FC<ICode> = ({
    codeString
}) => {
    const codeRef = useRef<HTMLDivElement>(null);

    const clickHandler = (e: React.MouseEvent<HTMLDivElement>) => {
        let range = document.createRange();
        range.selectNodeContents(codeRef.current); // <-- Error here!!
        window.getSelection()?.removeAllRanges();
        window.getSelection()?.addRange(range);

        navigator?.clipboard?.writeText(codeString);
    };

    return (
        <div
          id="Code"
          className="Code"
          onClick={clickHandler}
          ref={codeRef}
        >
            { codeString }
        </div>
    );
}

这是因为 codeRef.current 可能是 nullHTMLDivElement 是否 selectNodeContents 只期望 Node.

您需要做的就是将 codeRef.current 包装成条件:

import React, { FC, useRef } from 'react'

interface ICode {
  codeString: string
}
export const Code: FC<ICode> = ({
  codeString
}) => {
  const codeRef = useRef<HTMLDivElement>(null);

  const clickHandler = (e: React.MouseEvent<HTMLDivElement>) => {
    let range = document.createRange();
    if (codeRef.current) {
      range.selectNodeContents(codeRef.current); // ok
      window.getSelection()?.removeAllRanges();
      window.getSelection()?.addRange(range);

      navigator?.clipboard?.writeText(codeString);
    }
  };

  return (
    <div
      id="Code"
      className="Code"
      onClick={clickHandler}
      ref={codeRef}
    >
      {codeString}
    </div>
  );
}

Playground