How to dynamically create a submenu in a contextmenu

Tags: #<Tag:0x00007f0b0343b330>

Hi,

I want to display a submenu inside a contextmenu, which contains options depending on the cell clicked.

If I hard code the submenu items like so, it renders ok:

contextMenu: {
 items: {
  anItem: {
   submenu: {
    items: [{key:'anItem:red', name:'red'}]
   }
  }
 }
}

But I try to bind items to an inline function call, where I could generate a dynamic list of items to bind, like so, the function doesn’t get invoked and the submenu doesn’t contain any items:

contextMenu: {
 items: {
  anItem: {
   submenu: {
    items: () => {
     return [{key:'anItem:red', name:'red'}];
    }
   }
  }
 }
}

How can I achieve this? Thanks

Welcome Jason,

Some time ago I created a submenu that changes a color of a select cell/row/column I think that it will help you to build your menu https://jsfiddle.net/handsoncode/x6dsb5fg/

Thank you for the response; unfortunately that’s not what I’m after.

If I extend your example to change the colours, I’d like to be able to say ‘Column A -> Color column’ only has the option to set ‘White’ or ‘Yellow’, whereas ‘Column B -> Color column’ only has the option to set ‘Red’.

Ahh ok. So you can use hidden in the menu. the syntax is

"remove_col": {
          hidden: function () {
            // if first row, disable this option
            return hot.getSelectedRangeLast().from.col !== hot.countCols() - 1;
          }
        }

where you can pass col and row.

I can see hidden would hide the entire menu item, but how does that work for submenu items? Extending your example, I also want to keep the ‘Color Column’ option, but change the visible submenu items depending on the context.

I’d thought there may be two options to do this, but can’t get either to work:

  1. The submenu is rendered with all options and hides the ‘invalid’ options when the user views the context menu. The issue here is the ‘hidden’ property doesn’t seem to be valid against the submenu items.
  2. The submenu attempts to freshly render the correct options every time (as per example in my original post), but it ends showing nothing.

Yes, it hides an option for desired cell (you can use rows and columns for conditions).

You can also try to use to pass updateSettings > contextMenu via afterOnCellMouseDown hook.
To do not call the hook logic if not needed I would add a condition at the beginning to run the logic if the mouse down returns RMB key.

As previously said, I’ve tested the hidden attribute against the submenu items but it doesn’t work:

contextMenu: {
 items: {
  anItem: {
   submenu: {
    items: [{key:'anItem:red', name:'red'}, {key:'anItem:blue', name:'blue', hidden:true}];
    }
   }
  }
 }
}

In this example, the ‘blue’ submenu item should always be hidden, but it’s always visible.

Hey @jason.prouse

hidden has to be a function https://jsfiddle.net/handsoncode/5k2s4wbt/

This is poorly documented. I have added request to our ‘docs person’ to add it https://github.com/handsontable/docs/issues/79

1 Like