WinRT: Fix native MessageBox not closing
The message box buttons need to be added inside the XAML thread. Otherwise QWinRTMessageDialogHelper::onCompleted will not be triggered. To successfully emit the clicked signal across different threads do not exit the eventloop. Change-Id: Ie884bdfe0dc64132559755083dae50c2aa43d80b Task-number: QTBUG-48209 Reviewed-by: Oliver Wolff <oliver.wolff@theqtcompany.com>
This commit is contained in:
parent
676edc006e
commit
72d0c62d14
@ -133,45 +133,46 @@ bool QWinRTMessageDialogHelper::show(Qt::WindowFlags windowFlags, Qt::WindowModa
|
||||
RETURN_FALSE_IF_FAILED("Failed to create dialog");
|
||||
}
|
||||
|
||||
// Add Buttons
|
||||
ComPtr<IVector<IUICommand *>> dialogCommands;
|
||||
hr = dialog->get_Commands(&dialogCommands);
|
||||
RETURN_FALSE_IF_FAILED("Failed to get dialog commands");
|
||||
|
||||
// If no button is specified we need to create one to get close notification
|
||||
int buttons = options->standardButtons();
|
||||
if (buttons == 0)
|
||||
buttons = Ok;
|
||||
|
||||
for (int i = FirstButton; i < LastButton; i<<=1) {
|
||||
if (!(buttons & i))
|
||||
continue;
|
||||
// Add native command
|
||||
const QString label = d->theme->standardButtonText(i);
|
||||
HStringReference nativeLabel(reinterpret_cast<LPCWSTR>(label.utf16()), label.size());
|
||||
ComPtr<IUICommand> command;
|
||||
hr = commandFactory->Create(nativeLabel.Get(), &command);
|
||||
RETURN_FALSE_IF_FAILED("Failed to create message box command");
|
||||
ComPtr<IInspectable> id = Make<CommandId>(static_cast<StandardButton>(i));
|
||||
hr = command->put_Id(id.Get());
|
||||
RETURN_FALSE_IF_FAILED("Failed to set command ID");
|
||||
hr = dialogCommands->Append(command.Get());
|
||||
if (hr == E_BOUNDS) {
|
||||
qErrnoWarning(hr, "The WinRT message dialog supports a maximum of three buttons");
|
||||
continue;
|
||||
}
|
||||
RETURN_FALSE_IF_FAILED("Failed to append message box command");
|
||||
if (i == Abort || i == Cancel || i == Close) {
|
||||
quint32 size;
|
||||
hr = dialogCommands->get_Size(&size);
|
||||
RETURN_FALSE_IF_FAILED("Failed to get command list size");
|
||||
hr = dialog->put_CancelCommandIndex(size - 1);
|
||||
RETURN_FALSE_IF_FAILED("Failed to set cancel index");
|
||||
}
|
||||
}
|
||||
|
||||
hr = QEventDispatcherWinRT::runOnXamlThread([this, d, dialog]() {
|
||||
hr = QEventDispatcherWinRT::runOnXamlThread([this, d, options, commandFactory, dialog]() {
|
||||
HRESULT hr;
|
||||
|
||||
// Add Buttons
|
||||
ComPtr<IVector<IUICommand *>> dialogCommands;
|
||||
hr = dialog->get_Commands(&dialogCommands);
|
||||
RETURN_HR_IF_FAILED("Failed to get dialog commands");
|
||||
|
||||
// If no button is specified we need to create one to get close notification
|
||||
int buttons = options->standardButtons();
|
||||
if (buttons == 0)
|
||||
buttons = Ok;
|
||||
|
||||
for (int i = FirstButton; i < LastButton; i<<=1) {
|
||||
if (!(buttons & i))
|
||||
continue;
|
||||
// Add native command
|
||||
const QString label = d->theme->standardButtonText(i);
|
||||
HStringReference nativeLabel(reinterpret_cast<LPCWSTR>(label.utf16()), label.size());
|
||||
ComPtr<IUICommand> command;
|
||||
hr = commandFactory->Create(nativeLabel.Get(), &command);
|
||||
RETURN_HR_IF_FAILED("Failed to create message box command");
|
||||
ComPtr<IInspectable> id = Make<CommandId>(static_cast<StandardButton>(i));
|
||||
hr = command->put_Id(id.Get());
|
||||
RETURN_HR_IF_FAILED("Failed to set command ID");
|
||||
hr = dialogCommands->Append(command.Get());
|
||||
if (hr == E_BOUNDS) {
|
||||
qErrnoWarning(hr, "The WinRT message dialog supports a maximum of three buttons");
|
||||
continue;
|
||||
}
|
||||
RETURN_HR_IF_FAILED("Failed to append message box command");
|
||||
if (i == Abort || i == Cancel || i == Close) {
|
||||
quint32 size;
|
||||
hr = dialogCommands->get_Size(&size);
|
||||
RETURN_HR_IF_FAILED("Failed to get command list size");
|
||||
hr = dialog->put_CancelCommandIndex(size - 1);
|
||||
RETURN_HR_IF_FAILED("Failed to set cancel index");
|
||||
}
|
||||
}
|
||||
|
||||
ComPtr<IAsyncOperation<IUICommand *>> op;
|
||||
hr = dialog->ShowAsync(&op);
|
||||
RETURN_HR_IF_FAILED("Failed to show dialog");
|
||||
@ -206,8 +207,7 @@ HRESULT QWinRTMessageDialogHelper::onCompleted(IAsyncOperation<IUICommand *> *as
|
||||
Q_UNUSED(status);
|
||||
Q_D(QWinRTMessageDialogHelper);
|
||||
|
||||
if (d->loop.isRunning())
|
||||
d->loop.exit();
|
||||
QEventLoopLocker locker(&d->loop);
|
||||
|
||||
d->shown = false;
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user