I am attempting to migrate from Infragistics v7,3 to v16.2.
So far this has been mostly painless, however for some reason the existing code which dynamically changes the context menu based on data that is present in the row you are right clicking on, is no longer working as expected.
I have verified that our 'mergeMenus' method is in fact adding the 'sourceMenu' items to the 'targetMenu':
public static void MergeMenus(PopupMenuTool targetMenu, PopupMenuTool sourceMenu) { if (targetMenu != null && sourceMenu != null) { //Add source tools into target menu... int count = 0; ToolBase addedTool; foreach (ToolBase tool in sourceMenu.Tools) { if ( !targetMenu.Tools.Exists(tool.Key) ) { addedTool = targetMenu.Tools.AddTool(tool.Key); addedTool.InstanceProps.IsFirstInGroup = tool.InstanceProps.IsFirstInGroup; count++; } } //Group merged source items... if (count > 0) targetMenu.Tools[targetMenu.Tools.Count - count].InstanceProps.IsFirstInGroup = true; } }
All the tools are present in the targetMenu (though they are not visible on screen) and have all properties set exactly the same as those tools who are visible except:
AttachedParentTool is null and UIElement is null. Unfortunately these are read only properties and I cannot find any documentation on how these values should be properly initialized. I'm not even sure if this is causing the problem or not. Am I missing something?
So to make it even simpler, I tried adding a dummy ButtonTool like this:
var newTool = new ButtonTool("FunkyChicken") { SharedProps = { Caption = "TEST", Category = "InvalidWithNoReport", ToolTipText = "TESTING..." }, InstanceProps = { IsFirstInGroup = true } }; ContextMenuBase.ToolbarsManager.Tools.Add(newTool); ContextMenuBase.Tools.AddTool("FunkyChicken");
Unfortunately, this new tool does not show up either.
Hello Filip,
Thank you for contacting Infragistics!
The best way for us to assist you is if you provide a small isolated sample that we can run and use for debugging locally.
After building a very stripped down version, I cannot reproduce this problem. So there must be some interaction between the various layers of inheritance + event handlers that works fine in v7.3 but causes issues in v16.2. The project is proprietary and large so posting it is not an option.
If you cannot reproduce the problem by starting a new project and building up from there, perhaps you could try the other way - make a copy of your real application and then reduce it down to something that just reproduces the issue.
I will see if this is feasible (this would take a lot of time). In the meantime, can you think of a reason why a PopupMenuTool is displaying tools out of order? The items in the Tools collection are in the correct order, what is displayed on screen is in a different order. I used arrays of tools in the correct order and the used Tools.AddRange to build up a Tools collection that is in the order I want but what is displayed is incorrect.
When the menus are merged between the Mdi Parent and Mdi child, the merge behavior and order of the tools is determined by the MergeOrder and MergeType properties. Frankly, I'm not an expert on tool merging. It's quite complicated.
So, I am one step closer with this reply, thank you Mike. I have added MergeType = Replace and MergeOrder = 999 (so that whenever I add/remove a tool it is added to the bottom, this is what I want so not necessarily a 'universal' fix for anyone else reading this). I also had to add: myToolmanager.MdiParentManager.RefreshMerge(); wherever I am pro grammatically altering the menu, otherwise the changes are not reflected on Screen.
Now I have an issue where other submenu popups coming off the main context menu are appearing in odd locations, but this is most likely an artifact of my changes since other menus that don't dynamically change show their submenus correctly.
Ok, so the easiest solution was to simply set MdiMergeable to false. This feature was enable with an event handler in a base class (as I just now discovered) and my context menus had no need for it. It just caused more problems without any benefit so it seems that disabling it fixed everything. An entire day just to add one line of code... the joy of programming.
Ok, so I have verified that this is some bad interaction when calling toolManager.MdiParentManager.RefreshMerge(); inside BeforeToolDropdown
If I comment this out, then rebuilding the popumenu does not cause errors, but also does not update the screen.
It appears that Refreshing the merge of the MdiParent somehow negatively affects Showpopup. Any idea how to get around this?
Ok, so I can't find a reliable way to check if the popup is open already so I have worked around this by checking the tool contents, if a certain tool is present then I know it's open... not elegant but it works.
The problem now is that when I rebuild the submenus, I am getting an null reference deep within the infragistics stack:
Object reference not set to an instance of an object.
at Infragistics.Win.UltraWinToolbars.ToolMenuItem.get_DrawAsPressed() at Infragistics.Win.UltraWinToolbars.ToolMenuItem.ResolveAppearance(AppearanceData& appearance, AppearancePropFlags& requestedProps, Boolean drawAsActive) at Infragistics.Win.UltraWinToolbars.MenuItemBase.GetTextAreaSize(Int32 widthConstraint) at Infragistics.Win.UltraWinToolbars.MenuItemBase.get_Size() at Infragistics.Win.UltraWinToolbars.MenuItemBase.get_CachedSize() at Infragistics.Win.UltraWinToolbars.MenuAgentBase.CalculateSizeRequiredForMenuItems(MenuItemsCollection menuItems, Int32 firstItemIndex, Boolean& displayMoreItemsChevron, Size& minSize, Size& preferredMinSize, Size& preferredSize, Size& maxSize) at Infragistics.Win.UltraWinToolbars.MenuAgentBase.CalculateRequiredDropDownSize(Size& minSize, Size& preferredMinSize, Size& preferredSize, Size& maxSize) at Infragistics.Win.UltraWinToolbars.PopupMenuAgent.CalculateRequiredDropDownSize(Size& minSize, Size& preferredMinSize, Size& preferredSize, Size& maxSize) at Infragistics.Win.UltraWinToolbars.PopupMenuAgent.GetPopupControl() at Infragistics.Win.UltraWinToolbars.MenuAgentBase.DropDown(Control owningControl, Point point, Rectangle exclusionRect, DropDownPosition dropDownPosition, Boolean delay, Boolean closeIfAlreadyOpen, Boolean alignRight, Boolean autocloseDropdown, SplitMonitorAction splitMonitorAction, Boolean showMiniToolbar) at Infragistics.Win.UltraWinToolbars.PopupToolBase.DropDown(Control owningControl, Point point, Rectangle exclusionRect, DropDownPosition dropDownPosition, Boolean delay, Boolean closeIfAlreadyOpen, Boolean alignRight, Boolean autocloseDropdown, Control sourceControl, SplitMonitorAction splitMonitorAction, Boolean showMiniToolbar) at Infragistics.Win.UltraWinToolbars.UltraToolbarsManager.ShowPopupHelper(PopupToolBase popupTool, Point screenPoint, Rectangle exclusionRect, DropDownPosition dropdownPosition, Control sourceControl, Control owner, Boolean alignRight, Boolean showMiniToolbar) at Infragistics.Win.UltraWinToolbars.UltraToolbarsManager.ShowPopupHelper(PopupToolBase popupTool, Point screenPoint, Rectangle exclusionRect, DropDownPosition dropdownPosition, Control sourceControl, Control owner, Boolean alignRight, Boolean showMiniToolbar) at Infragistics.Win.UltraWinToolbars.UltraToolbarsManager.ShowPopupHelper(PopupToolBase popupTool, Point screenPoint, Rectangle exclusionRect, DropDownPosition dropdownPosition, Control sourceControl, Control owner) at Infragistics.Win.UltraWinToolbars.PopupToolBase.ShowPopup(Point screenPoint)
What is curious is that if I ignore this exception (we catch and display exceptions in the app) and try to re-open the same context menu (without triggering a rebuild), then everything works fine. As soon as I click on a row that triggers a rebuild, I get this exception again.
So I believe this is because I rebuild the menu 'BeforeToolDropDown' so when the submenu is hovered over, the parent menu closes because it is rebuilt. To get around this I am trying to inspect the Popupmenutool to see if it is already open. Unfortunately checking myPopup.IsOpen is showing false even when the popup is visible on screen. Checking myPopup.InstanceProps.Visible shows 'Default' when the popup is open or closed. Any ideas what property reliably indicates if the popup is visible on screen?
Interesting, so the submenus are appearing in the correct locations, what is happening is once I mouse over the submenu, the parent menu closes automatically. Strange that this does not happen on the statically created submenus.