Windows UI Ribbon Framework Demo - Intro
This is a backport of the most basic Ribbon demo from my now 3-part series on using the Ribbon in twinBASIC. The code is virtually unchanged; just some minor syntax differences where I had taken advantage of some new language features, using oleexp.tlb for the interfaces and some APIs instead of tbShellLib, and locally defining some APIs. The resources are unchanged, and indeed I just used the .res file from that project. I wanted to at least bring the proof of concept basic one to VB6, but won't be backporting the others; tB is the future :)
Windows applications frequently make use of the UI Ribbon in newer applications, including Explorer, Office, Wordpard, etc. While there's some controls implementing this kind of toolbar from scratch, and some exorbitantly expensive commercial controls that may or may not use the OS component ::cough:: CodeJock ::cough:: there's not been an implementation using the simple COM interfaces Microsoft applications use. This shows a basic proof of concept for VB6.
NOTE: Must be compiled first in order to run from IDE!! Details below.
Requirements
-Windows 7 or newer; no Ribbon in earlier versions
-You'll need either the Windows SDK v7.0 or newer, or to otherwise have obtained uicc.exe and rc.exe from it or Visual Studio.
-Becoming familiar with the XML-based Ribbon Markup Language to create the .xml files describing controls and commands. A good example for learning the syntax also accompanies this demo, although the example itself is C++.
-For VB6, oleexp v6.4 or newer (IMPORTANT: This was released a few hours before this demo, you'll likely need to update... 6.3 has bugs in the Ribbon interfaces)
Note
I recommend the Ribbon Designer in the Delphi Ribbon Frame by JAM-Software. an open source project here on GitHub. While it's not written in tB or VB6, it can be compiled without issue from source if you don't want to download the binary from the free Delphi IDE. It's a GUI-based designer that greatly simplifies the process of generating the XML, although you will still want to familiaring yourself with it, since the tool doesn't explain how it all works.
For our first ribbon application, we'll use this simple one, based on a pure C version by Stephen Wiria.
We'll start from the xml:
Preparing the project files
Once you have the ribbon.xml file and a \Res folder containing the bitmap images for your controls, you can proceed to preparing the project.
1) Use uicc.exe to compile the XML. This is easiest if you have Visual Studio command prompt available, but you can substitute full paths or drop uicc.exe in the ribbon folder. We want not just the compiled file, but we want uicc to prepare a resource file containing all the strings and bitmaps correctly named so importation into twinBASIC is nice and simple. For this we use the following command:
uicc.exe ribbon.xml ribbon.bml /res:ribbon.rc /header:ribbon.h
We ask for the C++ header because it generates a list of #defines for all the commands that is easy to copy/paste into VB/tB and do a few find/replaces to make into consts.
2) The first file is the compiled binary file; while you can use that for manual importation, it's already copied into ribbon.rc, so you don't need to worry about that for our method.
3) Compile ribbon.rc with rc.exe -- this is simple, in the same prompt, just use rc ribbon.rc. This will produce a .res file, which you might already be familiar with.
4) Use Resource Hacker or a similar tool to add any non-Ribbon resources your project has (n/a for the demo); for some reason, VB6 seems unable to open the resource in the IDE to do it there.
After that you're ready to start in VB6!
If you're setting up a new project, you'll need use Project->Add File to add the .res file, and the References dialog to add a reference to oleexp. These are already done in the demo.
The form sets everything up, then the class handles the events the ribbon raises to let us know about command clicks and other information.
The Form code declares a variable for the UI Ribbon Framework coclass, the events class, and a handler for the command click it raises:
Code:
Private pFramework As UIRibbonFramework
Private WithEvents pUIApp As clsRibbonEvents
Private Sub Form_Load()
Set pFramework = New UIRibbonFramework
Set pUIApp = New clsRibbonEvents
pFramework.Initialize Me.hWnd, pUIApp
pFramework.LoadUI GetModuleHandleW(), StrPtr("APPLICATION_RIBBON")
End Sub
Private Sub Form_Terminate()
pFramework.Destroy
Set pFramework = Nothing
Set pUIApp = Nothing
End Sub
Private Sub pUIApp_OnRibbonCmdExecute(ByVal commandId As Long, ByVal verb As UI_EXECUTIONVERB, ByVal key As LongPtr, currentValue As Variant, ByVal commandExecutionProperties As IUISimplePropertySet, returnValue As Long)
LogMsg "You clicked: CommandId=" & commandId & ", Verb=" & verb
Select Case commandId
Case IDC_EXIT
Unload Me
End Select
End Sub
All of those interfaces are already declared in oleexp (or in tB, tbShellLib); that's the entirety of the form code. In the class, we have:
Code:
Private Sub IUICommandHandler_Execute(ByVal commandId As Long, ByVal verb As UI_EXECUTIONVERB, key As PROPERTYKEY, currentValue As Variant, ByVal commandExecutionProperties As IUISimplePropertySet)
Dim hr As Long
Dim pv As Variant
If VarPtr(currentValue) <> 0 Then
VariantCopy pv, currentValue
End If
RaiseEvent OnRibbonCmdExecute(commandId, verb, VarPtr(key), pv, commandExecutionProperties, hr)
If hr < 0 Then Err.Raise hr
End Sub
Private Sub IUICommandHandler_UpdateProperty(ByVal commandId As Long, key As PROPERTYKEY, currentValue As Variant, newValue As Variant)
Dim hr As Long
Dim pv As Variant
Dim pnv As Variant
Dim bValid As Boolean
If VarPtr(currentValue) <> 0 Then
VariantCopy pv, currentValue
End If
RaiseEvent OnRibbonUpdateProperty(commandId, VarPtr(key), pv, pnv, bValid, hr)
If bValid Then
VariantCopy newValue, pnv
End If
If hr < 0 Then Err.Raise hr
End Sub
Compile and run, that's all there is to it! **IMPORTANT** You'll need to create the EXE first to run from the IDE, because Windows needs a binary with the Ribbon UIFILE resource to initialize the Ribbon.
Be sure to check out the UIRibbonDemos GitHub Repository!
Move into the future with the true successor, what VB7 would have been and more, twinBASIC, where you can check out the Intermediate Ribbon Demo, the Gallery Intro Demo, and coming soon, the Advanced Demo!



