Всем привет. При создании контекстного меню для объекта есть
лайфхак по скрытию пункта меню, если объект не подходит по условиям.
При этом есть два варианта:
1. Первый - как в ссылке - установить значение Enable = false. При этом пункт в меню будет виден, но не будет доступен. Не подходит.
2. Второй - установить Visible = false. При этом пункт меню скрывается. Подходит.
Итак, пытаемся реализовать:
private static void AttachCreateAnalogContextMenu()
{
if (_intellectualEntityContextMenu == null)
{
_intellectualEntityContextMenu = new ContextMenuExtension();
//todo translate
var menuItem = new Autodesk.AutoCAD.Windows.MenuItem("MP:Create analog");
menuItem.Click += CreateAnalogMenuItem_Click;
_intellectualEntityContextMenu.MenuItems.Add(menuItem);
_intellectualEntityContextMenu.MenuItems.Add(new Autodesk.AutoCAD.Windows.MenuItem("MenuItem2"));
_intellectualEntityContextMenu.MenuItems.Add(new Autodesk.AutoCAD.Windows.MenuItem("MenuItem3"));
_intellectualEntityContextMenu.Popup += IntellectualEntityContextMenuPopup;
var rxObject = RXObject.GetClass(typeof(BlockReference));
Autodesk.AutoCAD.ApplicationServices.Application.AddObjectContextMenuExtension(rxObject, _intellectualEntityContextMenu);
}
}
private static void IntellectualEntityContextMenuPopup(object sender, EventArgs e)
{
if (sender is ContextMenuExtension contextMenuExtension)
{
try
{
var selectionResult = AcadHelpers.Editor.SelectImplied();
var menuEnable = false;
if (selectionResult.Status == PromptStatus.OK &&
selectionResult.Value.Count == 1)
{
using (var tr = AcadHelpers.Database.TransactionManager.StartOpenCloseTransaction())
{
var id = selectionResult.Value.GetObjectIds()[0];
if (tr.GetObject(id, OpenMode.ForRead) is BlockReference blockReference &&
ExtendedDataHelpers.IsApplicable(blockReference))
{
menuEnable = true;
}
tr.Commit();
}
}
contextMenuExtension.MenuItems[0].Visible = menuEnable;
contextMenuExtension.MenuItems[1].Visible = menuEnable;
contextMenuExtension.MenuItems[2].Visible = menuEnable;
}
catch
{
// ignore
}
}
}
private static void CreateAnalogMenuItem_Click(object sender, EventArgs e)
{
AcApp.DocumentManager.MdiActiveDocument.SendStringToExecute(
"_.mpESKDCreateAnalog ", false, false, false);
}
private static void DetachCreateAnalogContextMenu()
{
if (_intellectualEntityContextMenu != null)
{
var rxObject = RXObject.GetClass(typeof(BlockReference));
Autodesk.AutoCAD.ApplicationServices.Application.RemoveObjectContextMenuExtension(rxObject, _intellectualEntityContextMenu);
_intellectualEntityContextMenu = null;
}
}
Я добавил пару пунктов в меню для наглядности, хотя проблема наблюдается и с одним пунктом.
Итак, что имеем: при вызове контекстного меню для блока, который подходит по условиям, все хорошо:
А вот при вызове контекстного меню для другого блока наблюдаем следующее:
Т.е. ContextMenuExtension имеется и автокад его разделяет полосками (разделителями). А так как пункты меню скрыты, то остаются только разделители.
Есть идеи как убрать этот неприятный эффект?