18

我一直在尝试出色的Medium Editor。我一直遇到的问题是我似乎无法获得“工作”的链接。

最简单的是,这里有一些 HTML/JS 用于演示问题:

HTML:

<html>
<head>
  <script src="//cdn.jsdelivr.net/medium-editor/latest/js/medium-editor.min.js"></script>
  <link rel="stylesheet" href="//cdn.jsdelivr.net/medium-editor/latest/css/medium-editor.min.css" type="text/css" media="screen" charset="utf-8">
  <link rel="stylesheet" href="https://cdn.jsdelivr.net/medium-editor/latest/css/themes/beagle.min.css" type="text/css">
</head>
<body>
  <div class='editable'>
    Hello world.  <a href="http://www.google.com">link</a>
  </div>
</body>
</html>

Javascript:

var editor = new MediumEditor('.editable');

这个小提琴演示了这个问题(使用上面的代码)。

  • 如果您将鼠标悬停在链接上,则会出现一个弹出窗口。
  • 如果单击链接,则不会发生任何事情。
  • 如果单击弹出窗口,则会出现一个表单,您可以在其中编辑链接。

在我看来,点击链接应该把我带到链接所指向的任何地方href。使用该链接的唯一方法是右键单击并在新选项卡或新窗口中打开——我不想让我的用户这样做。

我觉得我必须在配置中遗漏一些简单的东西(Anchor Preview OptionsAnchor Form Options)。不幸的是,我没有看到它。

在我的实际应用程序中,我没有使用jQuery,但我正在使用angularjs. 如果不存在严格的中等编辑器答案,我可以回退到使用基本 JS 或 angularjs 提供的任何东西。

4

4 回答 4

11

我找到了如何绑定事件。

这是完整的活动列表https://github.com/yabwe/medium-editor/blob/master/CUSTOM-EVENTS.md

尝试将您的代码更改为

var editor = new MediumEditor('.editable')
    .subscribe("editableClick", function(e){if (e.target.href) {window.open(e.target.href)}})

https://jsfiddle.net/fhr18gm1/

于 2015-12-29T20:46:21.550 回答
3

contenteditable所以 medium-editor 是建立在对元素的内置浏览器支持之上的。当您实例化媒体编辑器时,它会将contenteditable=true属性添加到您提供的任何元素中。

默认情况下,由于文本现在是可编辑的(该contenteditable属性使浏览器将其视为所见即所得的文本),浏览器不再支持单击链接进行导航。因此,媒体编辑器并没有阻止这些链接点击的发生,浏览器本身就是将其作为使文本可编辑的一部分。

medium-editor 内置了与链接交互的扩展:

  • 锚扩展
    • 允许添加/删除链接
  • 锚预览扩展
    • 悬停链接时显示工具提示
    • 单击工具提示时,允许通过锚扩展编辑链接的 href

我认为编辑的潜在目标是这里的误解。编辑器允许编辑文本,并且为了添加/删除/更新链接,您需要能够在不自动导航的情况下单击它。这就是我认为的“编辑”模式。

但是,编辑生成的 html 是有效的 html,如果您将该 html 放入没有该contenteditable=true属性的元素中,一切都会按预期工作。我认为这是“发布模式”

我查看了 word 或 google docs 之类的编辑器,您会看到类似的行为,当您编辑文档时,链接不仅会在您单击它们时导航走,您实际上必须选择通过单独的导航来导航它们单击链接后的操作。但是,在文档的“已发布”版本上,单击链接实际上会打开一个浏览器窗口并在那里导航。

我认为这确实是一个很好的建议,可以作为对现有锚预览扩展的增强。也许悬停链接时出现的工具提示可能有多个选项(即编辑链接|删除链接|导航到URL)。

tldr;

通过内置的所见即所得支持 ( contenteditable) 在浏览器中“编辑”文本时,链接无法在点击时导航。当不在“编辑”模式下时,链接将按预期工作。这可以很好地增强媒体编辑器锚预览扩展。

于 2015-12-31T19:31:29.030 回答
0

在评论中处理@Valijon 的一些想法,我能够使用以下代码使其工作:

var iElement = angular.element(mediumEditorElement);

iElement.on('click', function(event) {
  if (
      event.target && event.target.tagName == 'A' &&
      event.target.href && !event.defaultPrevented) {
    $window.open(event.target.href, '_blank');
  }
});

我认为关键是显然编辑器让事件传播到祖先元素,所以我能够只听顶级编辑器元素的点击。

在这里,$window是 angular 的$window服务——如果你不使用angularjswindow会做的伎俩,我曾经angular.element简化事件监听器注册表,但你可以用老式的方式(或使用你选择的 JS 框架)来做。

于 2015-12-29T20:44:19.897 回答
0

当我问这个问题时,我真正想要的是在“编辑”模式下类似于 Google Docs 的行为(如 Nate Mielnik 所述)。我在 Medium Editor 跟踪器上打开了一个问题,他们决定不将其作为核心媒体编辑器的一部分来实现,但他们指出,他们很乐意有人将该功能添加为扩展。

因此,我决定按照建议将该功能作为扩展来实现。它可以作为MediumTools 1的一部分找到。该项目仍处于非常早期的阶段(例如,我没有做任何事情来使样式看起来更好,或者使用更好的缩小实践等,但我们很乐意接受拉取请求)。

代码的核心如下所示:

var ClassName = {
  INNER: 'medium-editor-toolbar-anchor-preview-inner',
  INNER_CHANGE: 'medium-editor-toolbar-anchor-preview-inner-change',
  INNER_REMOVE: 'medium-editor-toolbar-anchor-preview-inner-remove'
}

var AnchorPreview = MediumEditor.extensions.anchorPreview;
GdocMediumAnchorPreview = MediumEditor.Extension.extend.call(
  AnchorPreview, {

    /** @override */
    getTemplate: function () {
      return '<div class="medium-editor-toolbar-anchor-preview">' +
        '  <a class="' + ClassName.INNER + '"></a>' +
        '  -' +
        '  <a class="' + ClassName.INNER_CHANGE + '">Change</a>' +
        '  |' +
        '  <a class="' + ClassName.INNER_REMOVE + '">Remove</a>' +
        '</div>';
    },

    /** @override */
    createPreview: function () {
      var el = this.document.createElement('div');

      el.id = 'medium-editor-anchor-preview-' + this.getEditorId();
      el.className = 'medium-editor-anchor-preview';
      el.innerHTML = this.getTemplate();

      var targetBlank =
          this.getEditorOption('targetBlank') ||
          this.getEditorOption('gdocAnchorTargetBlank');
      if (targetBlank) {
        el.querySelector('.' + ClassName.INNER).target = '_blank';
      }

      var changeEl = el.querySelector('.' + ClassName.INNER_CHANGE);
      this.on(changeEl, 'click', this.handleClick.bind(this));

      var unlinkEl = el.querySelector('.' + ClassName.INNER_REMOVE);
      this.on(unlinkEl, 'click', this.handleUnlink.bind(this));

      return el;
    },

    /** Unlink the currently active anchor. */
    handleUnlink: function() {
      var activeAnchor = this.activeAnchor;
      if (activeAnchor) {
        this.activeAnchor.outerHTML = this.activeAnchor.innerHTML;
        this.hidePreview();
      }
    }
  });

作为解释,我只是使用媒体的原型继承来“子类化”原始/内置AnchorPreview扩展。我重写了getTemplate将附加链接添加到标记中的方法。然后我从 的基本实现中借了很多东西getPreview,但我在每个链接上都酌情绑定了新的操作。最后,我需要在单击“删除”时执行“取消链接”链接的操作,因此我为此添加了一个方法。使用 contenteditable 魔法(以确保它是浏览器撤消堆栈的一部分),取消链接方法可能会做得更好一些,但我没有花时间弄清楚这一点(尽管它会为任何有兴趣的人:-)。

1目前,它是唯一的部分,但我希望这会在某个时候改变。. .

于 2016-01-29T01:45:18.233 回答