如何检测菜单何时在 tinymce 4 中呈现?
How to detect when a menu is rendered in tinymce 4?
在 tinymce 4
中,菜单栏已呈现,但每个菜单仅在单击时呈现。
为了说明这一点,请注意菜单栏中的每个菜单都有 mce-menu
class。
在任何时候,如果没有菜单打开,如果您尝试获取菜单集,您将失败,因为它们尚未呈现:
var menuSet = $('.mce-menu');
// menuSet.length : 0
但是如果您单击菜单栏 header,比如说 insert
菜单,它将被渲染并打开。现在,保持打开状态,转到控制台并重试:
var menuSet = $('.mce-menu');
// menuSet.length : 1
你会看到打开的菜单。
现在,如果您关闭它,请单击打开的菜单中的任意位置,然后重试:
var menuSet = $('.mce-menu');
// menuSet.length : 1
...菜单未从 DOM 中删除。好消息:由于菜单被渲染了一次,我们可以获取并操作它。
我对每个 .mce-menu
元素进行了一些 DOM 操作,但现在我必须在第一次打开每个菜单时进行操作。
但是如何处理这样的事件?
我无法从官方文档、论坛或任何地方获得任何线索。
使用 tinymce,您可以通过 editor 对象完全自定义菜单按钮:
tinymce.init({
/*....*/
setup: function(editor) {
editor.addButton('mybutton', {
type: 'menubutton',
text: 'My button',
icon: false,
onclick: function(){
alert('Some Message');
},
menu: [{
text: 'Menu item 1',
onclick: function() {
alert('Some Message');
}
}]
});
}
/*....*/
});
很遗憾,您不能在文本 属性 中插入 html,但我认为您可以通过更多研究来做到这一点。也可以为菜单按钮的点击事件创建回调函数。
就我个人而言,我会使用 tinymce 官方 api 来修改 dom 而不是做一些其他事件驱动的 dom 操作。
你可以找到更多好的例子here
当然可以,但我们都对JS事件的管理方式了解不够。
我尝试用旧方法编写我的事件处理程序:
$('body').on('click', function() {
do_stuff();
});
虽然我必须用新的正确方法来做:
$('body').on('click', '.mce-btn', function() {
do_stuff();
});
有了这个,事件就得到了正确的管理。
尝试使用 onPostrender 功能:
editor.addMenuItem("mybtn", {
type: "menuitem",
name: 'mybtn',
onPostRender:function (){
// write your code here//
},
我通过编写一个专注于该目的的方便的 `Tinymce 4 插件解决了这个问题。
当然这个插件是开源的,遵循原始的 Tinymce 许可政策,GNU GPL v2 许可证。
Tinymce Plugin MenusController:
https://github.com/sirap-group/tinymce-plugin-menuscontroller
但是我还没有写文档,抱歉。
但是,您可以通过以下方式使用它:
安装插件
从 github 下载最新版本的 tarball,或者更好的是,从 bower 安装它:
bower install tinymce-plugin-menuscontroller
如果您不知道 bower
,请在此处查找:https://bower.io (npm i -g bower; bower --help
).
npm 包尚不可用,我会尽快提供(但欢迎 github 上的任何 Pull Request...)。
默认情况下,插件文件夹将被下载并放置在./bower_components
。如果你以同样的方式安装了 tinymce,你也有 ./bower_components/tinymce
或 ./bower_components/tinymce-dist
.
您不需要将脚本添加到您的index.html
文件中,因为如果您设置正确,tinymce 会自行加载它。
所以你需要:
符号链接到 tinymce 插件文件夹:
$ cd ./bower_components/tinymce/plugins
$ ln -s ../../tinymce-plugin-menuscontroller menuscontroller
在tinymce init中加载它。例如:
tinymce.init({
选择器:'textarea',
// [...]
插件:'menuscontroller'
})
获取插件实例:
var editor = window.tinymce.activeEditor
var menusCtl = editor.plugins.menuscontroller
// at this point, if menusCtl is undefined, something gone wrong in the setup step: please check the previous steps.
插件API (v0.2.1)
实例方法
获取菜单栏:
menusCtl.getMenubar()
通过注册名称获取每个菜单:
menusCtl.getMenuByName(String: name)
获取工具栏
menusCtl.getToolbars
活动
事件:menusController:mceMenuRendered
事件
渲染任何 tinymce 菜单时
$('body').on('menusController:mceMenuRendered', function (evt, menuDomNode) {
console.log(menuDomNode)
})
The menusController:mceMenuRendered
event is called one for each menu of the active editor menubar, when it is rendered, so when the user click the dropdown menu (File
link for the "file" menu, Insert
for the "insert" menu, etc...).
事件:menusController:mceMenuItemRendered:<menuDomID>
呈现任何菜单项时。假设我们创建了一个带有 my-custom-menu-item
标识符的菜单项。所以tinymce将它的DOM ID设置为my-custom-menu-item
。因此,MenusController 插件将创建并绑定到以下事件:
menusController:mceMenuItemRendered:my-custom-menu-item
因此您可以处理监听它的自定义菜单项的渲染事件:
$('body').on('menusController:mceMenuItemRendered:my-custom-menu-item',
function (evt, menuItemDomNode) {
console.log(menuItemDomNode)
}
)
菜单控制器API (v0.3.0+)
A the time of wrinting (Monday, mars the 13th, 2017), the last released version is the v0.2.1
. But the v0.3.0
is planned to be released soon, and will provide a new event, more useful than the last.
事件:menusController:mceMenuItemRendered
When you need to know the menu item ID to handle the event menusController:mceMenuItemRendered:<menuDomID>
and get the menu item DOM Node as callback argument, the event menusController:mceMenuItemRendered
don't needs it but provides it as callback argument for each new rendered menu item:
$('body').on('menusController:mceMenuItemRendered',
function (evt, menuItemID) {
console.log(menuItemID) // 'my-custom-menu-item'
// So you can hanlde all menu item even if you don't know its ID
// And you can also handle the DOM Node with the selector by ID
var selector = '#' + menuItemID
var menuItem = $(selector)
console.log(menuItem) // jQuery object (the menu item)
}
)
在 tinymce 4
中,菜单栏已呈现,但每个菜单仅在单击时呈现。
为了说明这一点,请注意菜单栏中的每个菜单都有 mce-menu
class。
在任何时候,如果没有菜单打开,如果您尝试获取菜单集,您将失败,因为它们尚未呈现:
var menuSet = $('.mce-menu');
// menuSet.length : 0
但是如果您单击菜单栏 header,比如说 insert
菜单,它将被渲染并打开。现在,保持打开状态,转到控制台并重试:
var menuSet = $('.mce-menu');
// menuSet.length : 1
你会看到打开的菜单。
现在,如果您关闭它,请单击打开的菜单中的任意位置,然后重试:
var menuSet = $('.mce-menu');
// menuSet.length : 1
...菜单未从 DOM 中删除。好消息:由于菜单被渲染了一次,我们可以获取并操作它。
我对每个 .mce-menu
元素进行了一些 DOM 操作,但现在我必须在第一次打开每个菜单时进行操作。
但是如何处理这样的事件?
我无法从官方文档、论坛或任何地方获得任何线索。
使用 tinymce,您可以通过 editor 对象完全自定义菜单按钮:
tinymce.init({
/*....*/
setup: function(editor) {
editor.addButton('mybutton', {
type: 'menubutton',
text: 'My button',
icon: false,
onclick: function(){
alert('Some Message');
},
menu: [{
text: 'Menu item 1',
onclick: function() {
alert('Some Message');
}
}]
});
}
/*....*/
});
很遗憾,您不能在文本 属性 中插入 html,但我认为您可以通过更多研究来做到这一点。也可以为菜单按钮的点击事件创建回调函数。
就我个人而言,我会使用 tinymce 官方 api 来修改 dom 而不是做一些其他事件驱动的 dom 操作。
你可以找到更多好的例子here
当然可以,但我们都对JS事件的管理方式了解不够。
我尝试用旧方法编写我的事件处理程序:
$('body').on('click', function() {
do_stuff();
});
虽然我必须用新的正确方法来做:
$('body').on('click', '.mce-btn', function() {
do_stuff();
});
有了这个,事件就得到了正确的管理。
尝试使用 onPostrender 功能:
editor.addMenuItem("mybtn", {
type: "menuitem",
name: 'mybtn',
onPostRender:function (){
// write your code here//
},
我通过编写一个专注于该目的的方便的 `Tinymce 4 插件解决了这个问题。
当然这个插件是开源的,遵循原始的 Tinymce 许可政策,GNU GPL v2 许可证。
Tinymce Plugin MenusController:
https://github.com/sirap-group/tinymce-plugin-menuscontroller
但是我还没有写文档,抱歉。
但是,您可以通过以下方式使用它:
安装插件
从 github 下载最新版本的 tarball,或者更好的是,从 bower 安装它:
bower install tinymce-plugin-menuscontroller
如果您不知道 bower
,请在此处查找:https://bower.io (npm i -g bower; bower --help
).
npm 包尚不可用,我会尽快提供(但欢迎 github 上的任何 Pull Request...)。
默认情况下,插件文件夹将被下载并放置在./bower_components
。如果你以同样的方式安装了 tinymce,你也有 ./bower_components/tinymce
或 ./bower_components/tinymce-dist
.
您不需要将脚本添加到您的index.html
文件中,因为如果您设置正确,tinymce 会自行加载它。
所以你需要:
符号链接到 tinymce 插件文件夹:
$ cd ./bower_components/tinymce/plugins $ ln -s ../../tinymce-plugin-menuscontroller menuscontroller
在tinymce init中加载它。例如:
tinymce.init({ 选择器:'textarea', // [...] 插件:'menuscontroller' })
获取插件实例:
var editor = window.tinymce.activeEditor
var menusCtl = editor.plugins.menuscontroller
// at this point, if menusCtl is undefined, something gone wrong in the setup step: please check the previous steps.
插件API (v0.2.1)
实例方法
获取菜单栏:
menusCtl.getMenubar()
通过注册名称获取每个菜单:
menusCtl.getMenuByName(String: name)
获取工具栏
menusCtl.getToolbars
活动
事件:menusController:mceMenuRendered
事件
渲染任何 tinymce 菜单时
$('body').on('menusController:mceMenuRendered', function (evt, menuDomNode) {
console.log(menuDomNode)
})
The
menusController:mceMenuRendered
event is called one for each menu of the active editor menubar, when it is rendered, so when the user click the dropdown menu (File
link for the "file" menu,Insert
for the "insert" menu, etc...).
事件:menusController:mceMenuItemRendered:<menuDomID>
呈现任何菜单项时。假设我们创建了一个带有 my-custom-menu-item
标识符的菜单项。所以tinymce将它的DOM ID设置为my-custom-menu-item
。因此,MenusController 插件将创建并绑定到以下事件:
menusController:mceMenuItemRendered:my-custom-menu-item
因此您可以处理监听它的自定义菜单项的渲染事件:
$('body').on('menusController:mceMenuItemRendered:my-custom-menu-item',
function (evt, menuItemDomNode) {
console.log(menuItemDomNode)
}
)
菜单控制器API (v0.3.0+)
A the time of wrinting (Monday, mars the 13th, 2017), the last released version is the
v0.2.1
. But thev0.3.0
is planned to be released soon, and will provide a new event, more useful than the last.
事件:menusController:mceMenuItemRendered
When you need to know the menu item ID to handle the event
menusController:mceMenuItemRendered:<menuDomID>
and get the menu item DOM Node as callback argument, the eventmenusController:mceMenuItemRendered
don't needs it but provides it as callback argument for each new rendered menu item:
$('body').on('menusController:mceMenuItemRendered',
function (evt, menuItemID) {
console.log(menuItemID) // 'my-custom-menu-item'
// So you can hanlde all menu item even if you don't know its ID
// And you can also handle the DOM Node with the selector by ID
var selector = '#' + menuItemID
var menuItem = $(selector)
console.log(menuItem) // jQuery object (the menu item)
}
)