首页 > 解决方案 > 如何在反应羽毛笔中插入主题标签和提及的链接?

问题描述

我使用react quill作为富文本编辑器,我使用quill 提及添加主题标签和在编辑器中提及的人。我已经阅读了羽毛笔提及的文档,但没有添加链接到插入的“主题标签”或“提及”的示例。

有用于添加链接的道具“linkTarget”,但没有将链接添加到主题标签和提及的示例。

来自数据库的哈希值和属性值:

hashvalues:[{
id:1,
value:"newHashtag"
}]

atvalues:[{
id:1,
value:"Jhon"
}]

所以我的预期输出是:对于标签:

<a href:`/#/hashtags/${id}`>#{value}</a>

人们提到:

<a href:`/#/people/${id}`>@{value}</a>

这是我的文本编辑器和提及模块的代码:

import React, { useEffect, useState } from "react";
import ReactQuill, { Quill } from "react-quill";
import * as Emoji from "quill-emoji";
import "react-quill/dist/quill.snow.css";
import "quill-emoji/dist/quill-emoji.css";
import "quill-mention/dist/quill.mention.css";
import "quill-mention";

//Add https to link if https is not present
const Link = Quill.import("formats/link");
Link.sanitize = function (url) {
  // quill by default creates relative links if scheme is missing.
  if (!url.startsWith("http://") && !url.startsWith("https://")) {
    return `http://${url}`;
  }
  return url;
};
Quill.register(Link, true);
Quill.register("modules/emoji", Emoji);

// Add sizes to whitelist and register them
const Size = Quill.import("formats/size");
Size.whitelist = ["extra-small", "small", "medium", "large"];
Quill.register(Size, true);

// Add fonts to whitelist and register them
const Font = Quill.import("formats/font");
Font.whitelist = [
  "arial",
  "comic-sans",
  "courier-new",
  "georgia",
  "helvetica",
  "lucida",
];
Quill.register(Font, true);

let atValues = [];
let hashValues = [];


const mention = {
  allowedChars: /^[A-Za-z\sÅÄÖåäö]*$/,
  mentionDenotationChars: ["@", "#"],
  linkTarget:"https://www.google.com",
  source: function (searchTerm, renderList, mentionChar, ) {
    let values;

    if (mentionChar === "@") {
      values = atValues;
    } else {
      values = hashValues;
    }

    if (searchTerm.length === 0) {
      renderList(values, searchTerm);
    } else {
      const matches = [];
      for (let i = 0; i < values.length; i++)
        if (~values[i].value.toLowerCase().indexOf(searchTerm.toLowerCase()))
          matches.push(values[i]);
      renderList(matches, searchTerm);
    }
  },
};

function Editor(props) {
  const [editorHtml, setEditorHtml] = useState("");

  const handleChange = (html) => {
    setEditorHtml(html);
    props.changeHandler(html);
  };

  useEffect(() => {
    if (props.value) {
      setEditorHtml(props.value);
    } else {
      setEditorHtml("");
    }
    if(props.values){
      let hash=props.values
      hash.map((v) => {
        v["value"] = v["display"]
      })
      hashValues=hash
    }
    if(props.people){
      let peoples = props.people
      peoples.map((v) => {
        v["value"] = v["display"]
      })
      atValues=peoples
    }
  }, [props.value]);

  return (
    <div>
      <ReactQuill
        onChange={handleChange}
        value={editorHtml}
        modules={modules}
        formats={formats}
        bounds={".app"}
        placeholder={props.placeholder}
      />
    </div>
  );
}

const modules = {
  toolbar: [
    [{ header: [1, 2, 3, 4, 5, 6, false] }],

    [{ list: "ordered" }, { list: "bullet" }],
    ["bold", "italic", "underline"],
    [{ color: [] }, { background: [] }],
    // [{ script: 'sub' }, { script: 'super' }],
    [{ align: [] }],
    ["link", "blockquote", "emoji"],
    ["clean"],
  ],
  clipboard: {
    // toggle to add extra line breaks when pasting HTML:
    matchVisual: false,
  },
  mention,
  "emoji-toolbar": true,
  "emoji-textarea": false,
  "emoji-shortname": true,
};

const formats = [
  "header",
  "font",
  "size",
  "bold",
  "italic",
  "underline",
  "strike",
  "blockquote",
  "list",
  "bullet",
  "indent",
  "link",
  "mention",
  "emoji",
];

export default function EMTextArea({
  placeHolder,
  name,
  value,
  changeHandler,
  hash,
  peopleMention
}) {
  return (
    <div className="custom-toolbar-example">
      <Editor
        placeholder={placeHolder}
        name={name}
        value={value}
        changeHandler={changeHandler}
        values={hash}
        people={peopleMention}
      />
    </div>
  );
}

我怎样才能做到这一点?谢谢你!

标签: reactjsreact-quill

解决方案


我解决了它,我必须在 atvalues 和 hashvalues 对象数组中添加“链接”键。

新的哈希值:

hashvalues:[{
id:1,
value:"hashtag",
link:"/#/users/hashtags/1"}]

并在提及模块中:

const mention = {
  allowedChars: /^[A-Za-z\sÅÄÖåäö]*$/,
  mentionDenotationChars: ["@", "#"],
  linkTarget: '_self',
  source: function (searchTerm, renderList, mentionChar, ) {
    let values;

    if (mentionChar === "@") {
      values = atValues;
    } else {
      values = hashValues;
    }

    if (searchTerm.length === 0) {
      renderList(values, searchTerm);
    } else {
      const matches = [];
      for (let i = 0; i < values.length; i++)
        if (~values[i].value.toLowerCase().indexOf(searchTerm.toLowerCase()))
          matches.push(values[i]);
      renderList(matches, searchTerm);
    }
  },
};

不管怎么说,还是要谢谢你。


推荐阅读