Windows Ribbon for WinForms, Part 18 – ContextPopup

27 בנובמבר 2009

תגובה אחת

Windows Ribbon for WinForms library now supports using a Context Popup.
The result of this post is a yet another sample, “15-ContextPopup”, found on the project site.


image


What is a Context Popup?
A context popup is a combination of a small toolbar (called MiniToolbar) and a context menu, which a ribbon enabled application can provide. This popup usually appears when right-clicking an application surface and it usually provide common operation relevant for the clicked surface.
Basically it’s just another way to get to your ribbon commands. In fact, since the MiniToolbar (the upper part of the context popup) can’t be access using the keyboard, Microsoft strongly recommends that every command should be also available using the standard ribbon interface.


More details can be found at Context Popup on MSDN.


Using ContextPopup – Ribbon Markup
Following is an example of defining a context popup. Only the Views section is presented since the Commands section is obvious. The result of this markup is shown in the image above.




<Application.Views>
  <ContextPopup>
    <ContextPopup.MiniToolbars>
      <MiniToolbar Name="MiniToolbar">
        <MenuGroup>
          <FontControl CommandName="cmdFontControl"/>
        </MenuGroup>
        <MenuGroup>
          <DropDownColorPicker CommandName="cmdDropDownColorPicker" />
          <Button CommandName="cmdButtonNew" />
          <Button CommandName="cmdButtonOpen" />
          <Button CommandName="cmdButtonSave" />
          <ComboBox />
        </MenuGroup>
      </MiniToolbar>
    </ContextPopup.MiniToolbars>
    <ContextPopup.ContextMenus>
      <ContextMenu Name="ContextMenu">
        <MenuGroup>
          <Button CommandName="cmdButtonNew" />
          <Button CommandName="cmdButtonOpen" />
          <Button CommandName="cmdButtonSave" />
        </MenuGroup>
        <MenuGroup>
          <DropDownColorPicker CommandName="cmdDropDownColorPicker" />
        </MenuGroup>
      </ContextMenu>
    </ContextPopup.ContextMenus>
    <ContextPopup.ContextMaps>
      <ContextMap CommandName="cmdContextMap"
                  ContextMenu="ContextMenu"
                  MiniToolbar="MiniToolbar" />
    </ContextPopup.ContextMaps>
  </ContextPopup>
  <Ribbon>
  </Ribbon>
</Application.Views>

Things to note:



  1. In the ContextPopup.MiniToolbars element you can define a list of available mini toolbars (upper parts).

  2. In the ContextPopup.ContextMenus element you can define a list of available context menus (lower parts).

  3. The actual definition of the context popup resides in the ContextPopup.ContextMaps element, where you can define a list of context popups. For each context popup you need to specify its upper part and lower part.

Using ContextPopup – Code Behind
In order to show the predefined context popups I present here two ways: the recommended way and the convenient way.


The recommended way
Use the method, Ribbon.ShowContextPopup to show a given context popup in a certain location, usually as a response to right clicking:




private Ribbon _ribbon;

public Form1()
{
    InitializeComponent();

    _ribbon = new Ribbon();

    // recommended way
    panel2.MouseClick += new MouseEventHandler(panel2_MouseClick);
}

void panel2_MouseClick(object sender, MouseEventArgs e)
{
    if (e.Button == MouseButtons.Right)
    {
        System.Drawing.Point p = panel2.PointToScreen(e.Location);
        _ribbon.ShowContextPopup((uint)RibbonMarkupCommands.cmdContextMap, p.X, p.Y);
    }
}

Note that the ShowContextPopup gets the location in screen coordinates, so a transformation using the Control.PointToScreen method is required.


The convenient way
If you are used to program client applications in .NET you must be familiar with ContextMenuStrip class. Every WinForms control has a ContextMenuStrip property where you can attach an instance of a predefined ContextMenuStrip instance, thus letting the .NET framework handle the opening of the context menu for you. Unfortunately the ContextMenuStrip property works only with ContextMenuStrip instances (An IContextMenuStrip interface would be great..), so you can’t easily replace the .NET implementation of a context menu with our new ribbon based implementation.


Following is a hack you can use to achieve this. I’ve created a RibbonContextMenuStrip class that inherits from ContextMenuStrip and hacked my way into showing the ribbon context menu instead of the .NET context menu. The advantage is that you have an easier interface for working with the ribbon context menu:




private Ribbon _ribbon;
private RibbonContextMenuStrip _ribbonContextMenuStrip;

public Form1()
{
    InitializeComponent();

    _ribbon = new Ribbon();
    _ribbonContextMenuStrip = new RibbonContextMenuStrip(_ribbon, (uint)RibbonMarkupCommands.cmdContextMap);

    // convenient way
    panel1.ContextMenuStrip = _ribbonContextMenuStrip;
}

As you can see from the code, it is shorter and use the standard .NET way for setting context menus on controls.


Let’s see the “magic” in action:




public class RibbonContextMenuStrip : ContextMenuStrip
{
    private uint _contextPopupID;
    private Ribbon _ribbon;

    public RibbonContextMenuStrip(Ribbon ribbon, uint contextPopupID)
        : base()
    {
        _contextPopupID = contextPopupID;
        _ribbon = ribbon;
    }

    protected override void OnOpening(CancelEventArgs e)
    {
        _ribbon.ShowContextPopup(_contextPopupID,
                                 Cursor.Position.X,
                                 Cursor.Position.Y);
        e.Cancel = true;
    }
}

Note: The RibbonContextMenuStrip is NOT part of the Windows Ribbon for WinForms library. The code is available as part of the sample “15-ContextPopup”. It works but I don’t like it.


Ribbon Properties
This section has nothing to do with context popup.


The ribbon library now supports 3 general properties for the ribbon UI:



  • Minimized – Specifies whether the ribbon is in a collapsed or expanded state.
    Property Identifier: UI_PKey_Minimized

  • Viewable - Specifies whether the ribbon user interface (UI) is in a visible or hidden state.
    Property Identifier: UI_PKey_Viewable

  • QuickAccessToolbarDock – Specifies whether the quick access toolbar is docked at the top or at the bottom.
    Property Identifier: UI_PKey_QuickAccessToolbarDock

Using these properties is as simple as:




private void Form1_Load(object sender, EventArgs e)
{
    _ribbon.InitFramework(this);
    _ribbon.Viewable = false;
}

That’s it for now,
Arik Poznanski.

kick it on DotNetKicks.com Shout it

הוסף תגובה
facebook linkedin twitter email

כתיבת תגובה

האימייל לא יוצג באתר. (*) שדות חובה מסומנים

תגובה אחת

  1. blogs.microsoft.co.il3 באפריל 2011 ב 10:19

    Windows ribbon for winforms part 18 contextpopup.. Amazing :)

    להגיב