Introduction
As you may or may not know, the MenuStrip
, ToolStrip
, ContextMenuStrip
, and StatusStrip
controls (hereafter called 'Strips' or 'Strip controls', for short) can be customized to a great extent. They use the ToolStrip(Professional)Renderer
class to render themselves, and it is possible to inherit this class and override the painting behavior. Of course, it takes a little effort to do that, as you are basically writing the drawing code manually.
If all you want is to change the colors of any of the Strip controls, but keep the shapes of everything (rectangular buttons, etc.), then there is a quicker way. The constructor of the ToolStripProfessionalRenderer
accepts a ProfessionalColorTable
, which is like a theme for the Strip controls. When supplied with a ProfessionalColorTable
, the ToolStripProfessionalRenderer
paints itself using the colors as specified in the ProfessionalColorTable
.
While that is a much quicker way to customize your Strip controls, it still forces you to write code (inherit the ProfessionalColorTable
class and override all color properties, returning your own values). These controls were designed to let you customize the colors of any of the Strip controls very easily, in the Visual Studio designer, without having to write a single line of code.
Furthermore, you change the colors in a component that can be re-used by as many Strip controls as you like. So, if you need a MenuStrip
and a ToolStrip
to look the same, you don't need to change their colors separately. You change the colors of this component, and they will use the same colors.
Also, your custom color definitions can be saved and loaded to and from XML files, so you can even distribute them to friends or coworkers.
Finally, there are 6 presets available that you simply have to choose from the list. The colors will then be set to mimic the colors for:
- Office 2007 (blue)
- Office 2003 Blue (default Windows XP style with Blue theme)
- Office 2003 Silver (default Windows XP style with Silver theme)
- Office 2003 Olive (default Windows XP style with Olive theme)
- Office XP (default Windows Vista / Windows 7 style)
- Office Classic (default style for Classic theme)
As you can see, the three default styles in Windows XP are also present, so you can even use the Silver theme in a Windows XP environment with a Blue theme.
Background
I made this as a project for myself. I thought it was odd that the .NET Framework provides the ability to customize the Strip controls, but doesn't provide it to the average user (e.g.: in the form of properties). I started out with a simple MenuStrip
control that provided the colors via properties, but as there are so many, the properties list became very long and unwieldy. It was also a problem that you had to set the colors a second time (on the ToolStrip
) when you wanted it to look the same. Or, even more times if you need more Strip controls. In short: it was still impractical.
With these controls, you only need to set the colors once, using properties in simple categories, and you can apply that theme to any Strip control you like.
Using the code
You don't need to write a single line of code to use these controls. All that is required are the following actions:
- Build the project containing the files.
- Drag an
AppearanceControl
(found in the toolbox after building) to your form. - Drag one or more Strip controls (found in the toolbox after building) to your form.
- Set the
Appearance
property of the Strip controls to the AppearanceControl
component on your form (use the dropdown in the property grid). - Explore the properties of the
AppearanceControl
. Use the Preset
property to set a preset theme, or use the CustomAppearance
property to change the colors manually. - In the Appearance Editor window that pops up, find the color property you need and change it. View the result instantly in the preview Strips.
Note: for the Strips to use the colors as defined in CustomAppearance
, the Preset
property must be set to Custom
.
Points of interest
How does it work?
The AppearanceControl
component uses an instance of a class that inherits ProfessionalColorTable
internally. Instead of returning hardcoded values, it returns the colors as set in the CustomAppearance
property:
Public Class CustomColorTable _
Inherits ProfessionalColorTable
Private ac As AppearanceControl = Nothing
Public Sub New(ByVal appearanceControl As AppearanceControl)
ac = appearanceControl
End Sub
Overrides ReadOnly Property ButtonSelectedHighlight() As Color
Get
Return ac.CustomAppearance.ButtonAppearance.SelectedAppearance.Highlight
End Get
End Property
Overrides ReadOnly Property ButtonSelectedHighlightBorder() As Color
Get
Return ac.CustomAppearance.ButtonAppearance.SelectedAppearance.BorderHighlight
End Get
End Property
End Class
In addition to this CustomColorTable
class, there is a ColorTable
for every preset which does use hardcoded color values.
The AppearanceControl
exposes a ToolStripProfessionalRenderer
, which has its ColorTable
set to one of the internal color table classes.
Finally, the Strip controls (CustomizableMenuStrip
, CustomizableToolStrip
, CustomizableContextMenuStrip
, and CustomizableStatusStrip
) listen for a change in their AppearanceControl
. When the Appearance
property is set, they change their renderer from the default renderer to the Renderer
property exposed by the AppearanceControl
.
Protected Overridable Sub OnAppearanceControlChanged(ByVal e As EventArgs)
If Me.Appearance IsNot Nothing Then
AddHandler Me.Appearance.AppearanceChanged, _
AddressOf AppearanceControl_AppearanceChanged
AddHandler Me.Appearance.Disposed, _
AddressOf AppearanceControl_Disposed
Me.Renderer = Me.Appearance.Renderer
Else
Me.Renderer = New ToolStripProfessionalRenderer()
End If
Me.Invalidate()
RaiseEvent AppearanceControlChanged(Me, e)
End Sub