Modifying a ribbon control at runtime - c++

I'm using the Windows Ribbon Framework in an unmanaged C++ application in Visual Studio.
Is it possible to add a button or other control at runtime? I can set up my ribbon using IUIFramework::LoadUI, but I can't modify it afterwards.

It is not possible to add or remove a button at runtime, but you may hide or show a Tab or Group at run time using Application Modes and you can set any button texts and images at runtime.
So you can declare and use multi-purpose buttons that will show only when a specific Application Mode is set and contain runtime defined texts and images.

You can switch modes at runtime depending on what is defined in the markup - see here for details:
After modes are defined in markup,
they can be easily enabled or disabled
in response to contextual events. As
mentioned previously, Ribbon
applications always start in the
default mode 0. After the application
has initialized and mode 0 is active,
the set of active modes can be changed
by calling the IUIFramework::SetModes
function.
There is a comment here to the effect that changes at runtime are quite limited - this is in regard to a third-party wrapper, note.
You can dynamically add items at
runtime only to the galleries
controls:
ComboBox, SplitButtonGallerty,
DropDownGallery and InRibbonGallery
If you know what you want to add from
advance you can use ContextualTabs and
ApplicationModes to change the
visibility of (predefined) tabs and
groups.
Unfortunately, you can add dynamically
groups at runtime.
Note this is a limitation in the
Windows Ribbon Framework and not in
the wrapper library.

Related

GTK: get rid of the system theme/CSS altogether

GTK3 applications can be styled and themed with CSS. How can I force GTK to use solely the CSS shipped with my application, instead of combining / cascading it with the theme installed on the user's system?
Why would one want to do that? In theory, CSS would be a great rules-based styling system, where you just add one screen full judiciously chosen rules to define the looks of your application consistently. Unfortunately, in practice, people tend to add hundreds of brain-dead, repetitious definitions into their stylesheets, thereby counterfeiting the very nature of cascading.
The actual problem is that my application shall get the typical, subdued dark-grey look of a media handling application, irrespective of the global theme installed on the user's system. From reading the GTK documentation and the GTKmm tutorial, I came up with the following code to read my own CSS stylesheet:
auto screen = Gdk::Screen::get_default();
auto css_provider = Gtk::CssProvider::create();
try {
css_provider->load_from_path(lib::resolveModulePath (stylesheetName, resourceSerachPath));
} catch(Glib::Error const& failure) {
WARN(gui, "Failure while loading stylesheet '%s': %s", cStr(stylesheetName), cStr(failure.what()));
}
Gtk::StyleContext::add_provider_for_screen(screen, css_provider, GTK_STYLE_PROVIDER_PRIORITY_APPLICATION);
Technically this works perfect. However -- now I am forced to work "against" the CSS rules present on the user's system. If I start with setting a suitable border colour in the default rule and a dark grey background and suitable text colour in a rule for GtkWindow, plus some rule for text entry fields, I get the desired look on some parts, but whenever the user's system theme adds a specific definition for some specific widget or widget combination, thereby repeating explicitly the colours instead of inheriting them from a generic rule, I need to add yet another specific rule into my application style sheet to fix that specific case. That is, the possibly ill-guided structure of the installed system theme forces my application stylesheet into the same ill-guided bad practice and have hundreds of single-case definitions repeating the same values over and over.
Questions
How can I tell GTK to use only my stylesheet for my application?
Is there any viable alternative, which is not so radical, yet still allows me to use CSS the way it was intended to be used (minimal set of rules + cascading)?
You can use the reset.css file from the GTK demos to unset all existing rules.
A less radical alternative might be to just ignore user themes other than the default. Presumably if a user has a theme built with bad CSS practices, they nonetheless like that theme. So why shouldn't they be able to view your application with their preferred theme?
as pointed out by #ptomato, you can install a CSS to effectively override any pre-existing other rules on the system. However, this also shows a way towards a less radical solution: just cancel out the problematic parts of the pre-installed theme.
How does it work?
We add catch-all rules to the CSS, i.e. rules which somehow select any possible element, or at least a complete subtree. This is achieved by using a wildcard * in the selector. And since we install our stylesheet with a higher priority (typically GTK_STYLE_PROVIDER_PRIORITY_APPLICATION), these rules will "stamp over" every specific rule which happens to be present with lower priority.
we can use the value unset to clear out a setting
we can use the value inherit to force the property to be derived from the parent widget's setting of this property.
Especially for the given problem to get "grey-subdued media application" look within a environment with a "light" theme, we can use
* {
color: inherit;
background-color: inherit;
}
...to cancel out only the problematic part of the pre-existing "light" theme, which is the background and colour setting. We can then set our own values once at a central point, and they will be inherited as expected.
We can even expand on that idea and treat further problematic settings within a given scope, by using the wildcard below a CSS contextual selector. And a key trick to get that right is to use the GTK+ inspector on your running application and investigate the actual settings to find the lowest possible point still to "grab" the problematic setting. (To activate the GTK+ inspector run your application with GTK_DEBUG=interactive path/to/my/app )

Disabling a ComboBox item in Win32 API

I would like to disable an item in a combobox in my Win32 application (C++). I'm not quite sure how to do this. I'm trying to achieve something that looks like this:
Notice how CollectionItem2 and 3 are greyed-out.
Any help would be very much appreciated!
If you truly need a combobox for this, then (as #IInspectable said) you'll need to do a custom drawn control. Basically, you'll have to store some information saying which items are disabled/grayed, and draw the items appropriately based on whether they're enabled or not.
There may be a somewhat easier way though. This is normally done with a Split Button. This is button with the BS_SPLITBUTTON style set. When the drop-down part of the button is clicked, it sends a BCN_DROPDOWN notification.
You normally respond to that by displaying a menu, typically using TrackPopupMenu to display it immediately below the button (or immediately to its right, if you prefer). This is a normal menu, so it can have items enabled, disabled, grayed, have check boxes, etc., as you see fit.
If you're using MFC, it has a CSplitButton class that wraps the Split Button, simplifying the code a little bit--you can pass an identifier of a menu and sub-menu when you create the CSplitButton object, and it handles things from there.
A sample result probably looks pretty familiar:
Note: MFC also has a CMfcMenuButton class. This has roughly similar functionality, but is somewhat clumsier to use. If memory serves, it is compatible with older versions of Windows (but the split button goes back to Vista, so it's fine unless you really need to support XP).

Displaying the preferred accelerator in MFC feature pack menus and tooltips

We have converted an existing MFC application to use the MFC Feature Pack, retaining menus and toolbars rather than ribbons. It has two shortcuts defined in the accelerator resources for Cut, Ctrl+X and Shift+Delete. The older version of the program advertises the preferred shortcut of Ctrl+X in the second column of the menu and in brackets at the end of the tooltip for the toolbar icon. The feature pack, however, sets these up for itself by calling CKeyboardManager::FindDefaultAccelerator(), which returns Shift+Delete.
Is there a way to set up the accelerator resources so that the program displays the preferred shortcut, or some other way?

How to add or remove textboxes by changing the options in the combobox in Visual c++?

I want to know that whether I can add a textbox or label by changing the options in combo box. For example, I have 2 options in Combobox. If I choose the #1, it must show me 2 textboxes, but if I choose #2 it must show 3 textboxes.Can I do something like this in Visual Studio C++?
This can be done in two ways:
Dynamically create and destroy the edit controls using CreateWindowEx and DestroyWindow.
Statically create your GUI with 3 edit controls and set the visibility of the controls based on the selection using ShowWindow.
Have as many text-boxes you want. But hide them.
Handle CBN_SELCHANGE (ON_CBN_SEL_CHANGE in MFC).
In the handler, show (or hide) the text boxes depending on selection.
Showing/hiding text boxes aren't good from UI perspective. You better enable/disable them appropriately. You may put alternate text when they are disabled, and bring back original change when they have to be enabled.
Creating textboxes at runtime, and then deleting them isn't' good approach. You will need to keep track of Win32 UI handle and/or MFC object. This approach will also need more of UI resource creation/deletion, parent-child relationship handling et. al.

Dropdown height bug in CComboBox (common controls 6.0)?

I've made a simple MFC application (Visual Studio 2008, dialog based) and added a CComboBox using the resource editor. I used the resource editor to specify the dropdown height. Then I added some code to add 100 texts to the combobox. If I run this simple application the dropdown height is ignored. If I disable the Microsoft.Windows.Common-Controls 6.0.0.0 style (disable the pragma that adds it to the manifest file) then everything works fine.
Has anyone noticed this behaviour (and knows a solution)? I've searched the web and msdn, but no luck so far.
The only solution I've found (thx to someone on the Microsoft MFC newsgroup) is to use the CBS_NOINTEGRALHEIGHT flag that states that the combobox must look to the exact size specified by the user rather then adjusting it automatically (the reason this is a patch is that the flag is normally intended to disable the feature where the dropheight is adjusted so that no partial items are rendered).
The difference is the "new" Common-Controls-6.0-style Combo-box, or the "original" old-style Combo-box (pre 6.0).
I guess Microsoft finally "fixed" the ComboBox control so it dynamically changes the height of the drop-down according to the number of items and the screen real-estate available, which is better than having a fixed height (IMHO).
Unfortunately I have no source for that, just wild guessing :)