动态更改 jquery 上下文菜单

Dynamically change jquery contextmenu

我正在使用这个 jquery plugin。菜单的实例化如下所示:

$.contextMenu({
    selector:'.disposition-menu',
    zIndex: 120,

    callback: function(key, options) {
        var stepID = $(this).closest('.card').attr("id").substring(5);
        handle_disposition(key,stepID);

    },
    items: {
        "pin": {name: "Pin to top"},
        "unpin": {name:"Unpin"},
        "complete": {name: "Mark step completed"},
        "remove": {name: "Remove step from Map"},
   },
   events: {
       show: function(){}, //this is where I'm lost
       hide: function(){} //this is where I'm lost
   },
    trigger: 'hover'
}); 

'handle disposition' 函数与 php 和数据库交互,将“.card”记录为固定或取消固定在数据库中,以便在重新加载页面时正确显示。 HTML 是一张 bootstrap 4 牌,像这样:

<div class="card" >
    <div class="card-header ">
        <table class="title-table">
            <tr>
                <td>...</td>
                <td>...</td>
                <td>...</td>
                <td class="disposition-menu">&vellip;</td>
            </tr>
        </table>
    </div>

    <div class="card-body">
        ...{body content}
    </div>
</div>

我想做的是在固定和取消固定菜单项之间切换。一次只有其中一个应该出现在菜单上。如果该项目已经 "pinned"(即在数据库中标记,并由“.card”html 中的数据属性表示),则应该出现 "Unpin"...反之亦然。同样,一旦在菜单上单击 "Pin...",菜单应立即更改为隐藏 "Pin" 项并显示 "Unpin" 项,反之亦然

我查看了该插件的文档,但在使用带冒号的键(例如选择器: )和回调函数后,我还是个新手。该插件显然有一个 "visible:" key, and also "show:" and "hide:" keys (used as per this issue,但我不知道如何将这些元素串在一起以完成我的 objective。

使用build:

https://swisnl.github.io/jQuery-contextMenu/docs.html#build

If the build callback is found at registration, the menu is not built right away. The menu creation is delayed to the point where the menu is actually called to show.

$.contextMenu({
  selector: ".menu",
  build: function($trigger) {
    var options = {
      callback: function(key, options) {
        var m = "clicked: " + key;
        alert(m);
      },
      items: {}
    };

    if ($trigger.hasClass('pin')) {
      options.items.unpin = {name: "unpin"};
    } else {
      options.items.pin = {name: "pin"};
    }

    return options;
  }
});
.menu{
    width: 100px;
    padding: 10px;
    background: red;
    margin: 10px;
    color: #FFF;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<link href="https://cdnjs.cloudflare.com/ajax/libs/jquery-contextmenu/2.9.0/jquery.contextMenu.css" rel="stylesheet"/>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery-contextmenu/2.9.0/jquery.contextMenu.min.js"></script>

<div class="menu pin">Pin</div>
<div class="menu">Unpin</div>

点播示例:

https://swisnl.github.io/jQuery-contextMenu/demo/dynamic-create.html

编辑:

$.contextMenu({
  selector: ".disposition-menu",
  build: function($trigger) {
    var options = {
      callback: function(key, options) {
        if(key == "pin")
            $trigger.removeClass("unpin").addClass("pin");
        else if(key == "unpin")
            $trigger.removeClass("pin").addClass("unpin");
      },
      items: {}
    };

    if ($trigger.hasClass('pin')) {
      options.items.unpin = {name: "unpin"};
    } else {
      options.items.pin = {name: "pin"};
    }

    return options;
  }
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<link href="https://cdnjs.cloudflare.com/ajax/libs/jquery-contextmenu/2.9.0/jquery.contextMenu.css" rel="stylesheet"/>
<link href="https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0/css/bootstrap.min.css" rel="stylesheet"/>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery-contextmenu/2.9.0/jquery.contextMenu.min.js"></script>
<div class="card" >
    <div class="card-header ">
        <table class="title-table">
            <tr>
                <td>...</td>
                <td>...</td>
                <td>...</td>
                <td class="disposition-menu">&vellip;</td>
            </tr>
        </table>
    </div>

    <div class="card-body">
        ...{body content}
    </div>
</div>

这是我解决“菜单项交换”问题的方法。感谢@ahed-kabalan 为我指明了正确的方向。

HTML 与我在上面发布的问题没有变化。为了方便起见,这里再次说明:

<div class="card" >
    <div class="card-header ">
        <table class="title-table">
            <tr>
                <td>...</td>
                <td>...</td>
                <td>...</td>
                <td class="disposition-menu">&vellip;</td>
            </tr>
        </table>
    </div>

    <div class="card-body">
        ...{body content}
    </div>
</div>

修改JS,在点击特定菜单项并使用可见键时触发回调。此解决方案包括单击时修改的菜单项和不受影响的菜单项。菜单在悬停时出现,回调仅在菜单项选择时触发。取消固定项目默认设置为 visible: false - 即最初只有 pin 选项会出现在菜单中。由于 build 真正专注于构建一个全新的菜单,因此对我来说没有必要。 JS 现在看起来像这样:

$.contextMenu({
    selector:'.disposition-menu',
    zIndex: 120,
    callback: function(key, options) {
        
        var stepID = $(this).closest('.card').attr("id").substring(5);
        alert(stepID);
        handle_disposition(key,stepID);
        
    },
    items: {
        "pin": {name: "Pin to top",
            callback: function(key, opt) {
                opt.items['pin'].visible = false;
                opt.items['unpin'].visible = true;
            }
        },
        "unpin": {name:"Unpin",
            callback: function(key, opt) {
                opt.items['pin'].visible = true;
                opt.items['unpin'].visible = false;
            }
        },
        "complete": {name: "Mark step completed"},
        "remove": {name: "Remove step from Map"}
   },
   trigger: 'hover'
});

希望其他人会觉得这有用!