Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We鈥檒l occasionally send you account related emails.

Already on GitHub? Sign in to your account

File dialog controls #7256

Draft
wants to merge 5 commits into
base: main
Choose a base branch
from
Draft

Conversation

miloush
Copy link
Contributor

@miloush miloush commented Nov 5, 2022

Fixes #6346

Note: This PR is based on #7244. For review, see the individual commits, most notably 2e7aab3 and 74d617c. I can rebase if #7244 was not going in.

Description

Legacy (Windows XP) file dialog had a flag for showing a read-only checkbox, controlled by OpenFileDialog.ShowReadOnly. The IFileDialog API used since Vista does not have such flag, but the code has not been updated. As a result, ShowReadOnly and ReadOnlyChecked properties do not work.

This PR fixes the issue by matching the IFileDialog API fallback for legacy applications, i.e. by adding dropdown items to the OK button:

ShowReadOnly = true; ReadOnlyChecked = false:
image

ShowReadOnly = true; ReadOnlyChecked = true:
image

The strings come from comdlg32.dll resources and will be in the language of the OS.

Implementation

In order to support the drop-down items on the OK button, IFileDialogCustomize and IFileDialogControlEvents were implemented (together with IFileDialog2 for customizing the Cancel button). Controls can be added to all of OpenFileDialog, SaveFileDialog and OpenFolderDialog.

For example,

var dialog = new SaveFileDialog();
dialog.Filter = "All files (*.*)|*.*";

var radioGroup = new FileDialogVisualGroup("RadioButtonList");
radioGroup.Add(new FileDialogRadioButtonList("_radio 1", "r_adio 2", "ra_dio 3"));
dialog.CustomControls.Add(radioGroup);

var checkGroup = new FileDialogVisualGroup("CheckButtons");
checkGroup.Add(new FileDialogCheckButton("_check 1"));
checkGroup.Add(new FileDialogCheckButton("c_heck 2", false));
checkGroup.Add(new FileDialogCheckButton("chec_k 3", true));
dialog.CustomControls.Add(checkGroup);

var menuGroup = new FileDialogVisualGroup("Menus and separator");
menuGroup.Add(new FileDialogMenu("_menu 1", "item _1", "item _2"));
menuGroup.Add(new FileDialogSeparator());
menuGroup.Add(new FileDialogMenu("m_enu 2", "item"));
dialog.CustomControls.Add(menuGroup);

var comboGroup = new FileDialogVisualGroup("ComboBoxes");
comboGroup.Add(new FileDialogComboBox("item _1", "item &2", "item 3"));
comboGroup.Add(new FileDialogComboBox("item _1", "item &2", "item 3") { SelectedIndex = 1 });
dialog.CustomControls.Add(comboGroup);

var textGroup = new FileDialogVisualGroup("Text and EditBo_x");
textGroup.Add(new FileDialogText("Generic _label"));
textGroup.Add(new FileDialogEditBox("a text box 馃槉"));
dialog.CustomControls.Add(textGroup);

var pushButton = new FileDialogPushButton("A button not in a _group");
pushButton.Click += delegate { MessageBox.Show("Clicked!"); };
dialog.CustomControls.Add(pushButton);
            
var prominentGroup = new FileDialogVisualGroup("Pro_minent control", new FileDialogComboBox());
dialog.CustomControls.Add(prominentGroup);
dialog.CustomControls.Prominent = prominentGroup;

dialog.OkButton.Items.Add("_Add");
dialog.OkButton.Items.Add("Add a_ll");
dialog.CancelButton.CustomLabel = "_Done";

dialog.ShowDialog();

gives:

image

A new Microsoft.Win32.Controls namespace is introduced. The public classes and members are as follows:

CustomControls

New members on CommonItemDialog:

  • CustomControls
  • OkButton
  • CancelButton

Remaining work:

  • move exception messages to resources
  • add more dialog events, e.g. filter index changed is critical for many custom controls scenarios
  • check the string resources haven't moved since Vista
  • debugger display attributes

Customer Impact

Not taking this fix leaves the read-only properties broken.

Furthermore, customers must rely on alternative solutions for file dialog controls. Many applications, from Notepad to Office to Visual Studio, use custom controls in their file dialogs.

Regression

No.

Testing

Manual testing using 7.0.100-rc.2.22477.23. Ensured ReadOnlyChecked is respected when dialog is shown and reflects the correct value when dialog is confirmed.

Ensured all controls render, their state can be read after dialog is confirmed and is reverted when the dialog is cancelled. Limited testing of dynamically adding and removing items and changing controls' labels, visibility and status while the dialog is shown.

Risk

Medium. While the existing code already heavily depends on comdlg32.dll, this fix introduces an extra dependency on 3 of its resource strings. Alternatively these strings could be separately localized as part of WPF, but that might result in an inconsistencies since the language coverage of OS and WPF localization differs.

Furthermore, the controls introduce a possibility for the dialogs to be easily manipulated while they are being shown, which has not been possible before. While the existing properties are mostly read when the dialog is shown and updated when it is closed, a review should be done on whether they could and should be "live".

/cc @KirillOsenkov

Microsoft Reviewers: Open in CodeFlow

@ghost ghost assigned miloush Nov 5, 2022
@ghost ghost added the PR metadata: Label to tag PRs, to facilitate with triage label Nov 5, 2022
@ghost ghost requested review from dipeshmsft and singhashish-wpf November 5, 2022 00:46
@ghost ghost added the Community Contribution A label for all community Contributions label Nov 5, 2022
@miloush miloush mentioned this pull request Nov 5, 2022
24 tasks
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
API Review Requested Community Contribution A label for all community Contributions draft PR metadata: Label to tag PRs, to facilitate with triage
Projects
None yet
Development

Successfully merging this pull request may close these issues.

OpenFileDialog.ShowReadOnly does not work
2 participants