One of the really cool new features of Office 2007 is the new Ribbon UI, with the corresponding extensibility model called RibbonX. While there are a few resources available describing what RibbonX is, and how to format the XML, there’s little information available yet on how to use code to handle the events of your RibbonX buttons. In this post I’ll elaborate a bit about what the signature of your event handler should be. RibbonX is a bit unforgiving at the moment, when the signature is wrong, nothing gets called and you will not be notified.
As far as I am aware, there are three types of button controls you can place on a ribbon; buttons, togglebuttons and galleries. Let’s go over the XML markup and the event handler method for each of these types.
First of, a simple button. In RibbonX, a button is created using the following markup (for a more exhaustive review of the markup, check this blog):
<button id="demoButton" imageMso="HappyFace"
label="demoButton" onAction="DemoButtonAction" size="large"/>
The ‘onAction’ attribute points to a public method in the class which implements IRibbonExtensibility. This method needs the following signature, with the name corresponding to the one found in the ‘onAction’ attribute:
void DemoButtonAction(Office.IRibbonControl control)
Not too hard eh? It gets a bit more difficult to get the signature right for the ToggleButton:
<toggleButton id="demoToggleButton" imageMso="HappyFace"
label="demoToggleButton" onAction="DemoToggleButtonAction" size="large"/>
With a corresponding method signature:
void DemoToggleButtonAction(IRibbonControl control, bool pressed)
This one was easy enough as well. Now for the one I’m actually writing this post for; the Gallery. The Gallery is a bit more difficult, because the method signatures aren’t documented yet. First some XML markup:
<gallery id="demoGallery"
imageMso="FlyoutAnchorMovie"
onAction="DemoGalleryAction"
getItemCount="DemoGalleryGetItemCount"
getItemImage="DemoGalleryGetItemImage"
getItemLabel="DemoGalleryGetItemLabel">
And now for the difficult part, we need the signature of those four methods! Well, hold on to your horses, here it comes:
int DemoGalleryGetItemCount(IRibbonControl control)
IPictureDisp DemoGalleryGetItemImage(IRibbonControl control, int index)
string DemoGalleryGetItemLabel(IRibbonControl control, int index)
void DemoGalleryAction(IRibbonControl control, string id, int index)
Especially the last one was mean, I kept on trying a method without the string parameter and was lost!
Now for something extra. Do you notice the second method, you’ll need to return a IPictureDisp COM-thingy (scary stuff). How do you get a IPictureDisp when holding a dotnet Image instance? There are a few solutions:
1. Subclass the AxHost class, and call the protected static CreateIPictureDispFromPicture method. You’ll need to subclass because the method is protected.
class PictureDispFactory : AxHost
{
public PictureDispFactory()
: base(Guid.NewGuid().ToString("B"))
{
}
public static IPictureDisp CreateIPictureDisp(Image image)
{
return (IPictureDisp)AxHost.GetIPictureDispFromPicture(image);
}
}
2. Use a call to OleLoadPicture, which I’m currently testing.
Hope it helps!
PS: This is of course beta, and even worse, not a beta built by me. This code may change in the future. Also, this is not an exhaustive guide, expect those directly from Microsoft after the beta timeframe.