如何在tinyMCE中添加动态上下文菜单?

3
有没有办法在TinyMCE 4.x上的上下文菜单初始化后添加自定义动态元素?我创建了自定义菜单项,但其中许多子项依赖于应用程序中其他事物的进行。
我尝试使用editor.on('contextmenu'),但菜单仍然不会更新。有什么想法吗?
3个回答

3
  1. 添加 contextmenu 插件
  2. 通过定义 contextmenu 选项覆盖默认的上下文菜单(某些插件会自动添加它们自己的条目)。这是一个以管道符分隔的自定义菜单项列表(在步骤3中定义)。
  3. 定义自定义菜单项列表。这些可以有自己的 onclick 事件处理程序,或定义子菜单。

tinymce.init({
    ...
    plugins: [..., 'contextmenu'],
    contextmenu: 'customItem1 | customItem2',
    setup: function (editor) {
        editor.addMenuItem('customItem1', {
            text: 'Menu Item 1',
            context: 'tools',
            onclick: function () {
                alert('Menu item 1 clicked');
            }
        });
        editor.addMenuItem('customItem2', {
            text: 'Menu Item 2',
            context: 'tools',
            menu: [ {
                text: "Sub-menu item 1",
                onclick: function () {
                    alert('Sub-menu item 1');
                }
            }, {
                text: "Sub-menu item 2",
                onclick: function () {
                    alert('Sub-menu item 2');
                }
            }]
        });
    }
});

参考资料:


但是如何使子菜单项成为动态列表呢?我能够在tinymce启动时生成子菜单,但我需要该列表能够动态更改。 - kevin
2
@imnotfred,我认为没有一种特定于TinyMCE的方法可以实现你想要的功能。也就是说,你不能通过插件或任何直接的事件来实现它。 你需要绑定到contextmenu事件,在事件触发时使用preventDefault来阻止默认行为,然后显示一个自定义的上下文菜单(之前隐藏的一些HTML)。有很多关于如何创建自定义HTML/JS上下文菜单的资源。这里有一个 - Eric Lease
感谢提供信息和资源。不过,有点令人失望的是,tinyMCE并没有提供这个功能。 - kevin
editor.addMenuItem 现在应该改为 editor.ui.registry.addMenuItem。 - bfredo123
对于更新版本,请使用 editor.ui.registry.addMenuItem 而不是 editor.addMenuItem - Mubashar Abbas

0

这是我的做法 我使用了jQuery $.each来遍历我的对象,你也可以使用原生JavaScript

//register plugin to process context menu on a specific tag
tinymce.PluginManager.add('contextmenu-plugin', function (editor) {
  var selectedCode
  // Create a function which returns an array of items, these can be Submenus or Simple Items
  var contextMenuItems = () => { 
    return [
    {
      type: 'submenu',
      text: "Submenu 1",
      getSubmenuItems: () => {
        if (selectedCode){
          var contextMenuItems = []
          $.each( ArrayWithData, (index, data ) => {
            contextMenuItems.push({
              type: 'item',
              text: `${data}`,
              onAction: () => {
                console.log("Clicked submenu option");
              }
            })
          })
          // return array of contextmenuitems -> this goes to the Submenu
          return contextMenuItems
        }
       }
      },
      {  
       icon: 'remove',
       text: 'Remove data',
       onAction: () => {
         console.log(`Removed data`)
       }
      }
      }
      ]
      }

// now register the contextmenu
editor.ui.registry.addContextMenu('contextmenu', {
  update: function (element) {
    //this way you can call contextMenuItems() every time you show the context menu
    return (element.tagName == "your-condition" && element.className.includes("another condition") ) ? contextMenuItems() : ""
        }
      });
    });

0

是的,这是可能的。 JavaScript对象函数可用于在编辑器事件中动态声明值。 即使您可以使用循环,但仅支持一个菜单(因为上下文菜单值是唯一的),请制作虚拟上下文菜单并分别声明(应用您自己的逻辑)。

对于子菜单:要创建动态菜单,请使用数组,并通过JavaScript对象方法将其推入循环以动态显示。

参考资料:使用AngularJs在自定义TinyMCE编辑器中添加动态数据


1
你能否尝试更好地解释一下并编辑你的回答吗? - Homungus
在addMenuItem(dynamic_sub,{menu:object_methods});中调用JavaScript对象方法以便在子菜单中使用。对于动态上下文菜单,请使用相同的逻辑(addMenuItem(dynamic_sub,object_methods_context);)。 - Venkatesh Manohar

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接