Add Window menu for macOS and specify Help menu to AppKit (#12357)

* Add Window menu for macOS and specify Help menu to AppKit
* Fix potential NSString dangling pointers of temporary QStrings
This commit is contained in:
Sebastian Livoni 2025-11-02 16:16:22 +01:00 committed by GitHub
parent 9814037fd3
commit 6130a64be5
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
7 changed files with 65 additions and 2 deletions

View file

@ -157,6 +157,25 @@
<translation type="unfinished"></translation>
</message>
</context>
<context>
<name>AppKit</name>
<message>
<source>Window</source>
<translation type="unfinished"></translation>
</message>
<message>
<source>Minimize</source>
<translation type="unfinished"></translation>
</message>
<message>
<source>Zoom</source>
<translation type="unfinished"></translation>
</message>
<message>
<source>Bring All to Front</source>
<translation type="unfinished"></translation>
</message>
</context>
<context>
<name>ApplicationSettingsWidget</name>
<message>

View file

@ -93,6 +93,10 @@ MainWindow::MainWindow()
m_ui->setupUi(this);
#ifdef Q_OS_MACOS
macUtils()->configureWindowAndHelpMenus(this, m_ui->menuHelp);
#endif
#if defined(Q_OS_UNIX) && !defined(Q_OS_MACOS) && !defined(QT_NO_DBUS)
new MainWindowAdaptor(this);
QDBusConnection dbus = QDBusConnection::sessionBus();

View file

@ -21,6 +21,8 @@
#include <QColor>
#include <QObject>
#include <QMenu>
#include <QMainWindow>
#include <unistd.h>
class QWindow;
@ -45,6 +47,7 @@ public:
bool enableScreenRecording();
void toggleForegroundApp(bool foreground);
void setWindowSecurity(QWindow* window, bool state);
void configureWindowAndHelpMenus(QMainWindow* mainWindow, QMenu* helpMenu);
signals:
void userSwitched();

View file

@ -42,5 +42,6 @@
- (bool) enableScreenRecording;
- (void) toggleForegroundApp:(bool) foreground;
- (void) setWindowSecurity:(NSWindow*) window state:(bool) state;
- (void) configureWindowAndHelpMenus:(QMainWindow*) mainWindow helpMenu:(QMenu*) helpMenu;
@end

View file

@ -18,6 +18,8 @@
#import "AppKitImpl.h"
#import <QWindow>
#import <QMenu>
#import <QMenuBar>
#import <Cocoa/Cocoa.h>
#if __clang_major__ >= 13 && MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_VERSION_12_3
#import <ScreenCaptureKit/ScreenCaptureKit.h>
@ -184,7 +186,7 @@
//
// Check if screen recording is enabled, may show an popup asking for permissions
//
- (bool) enableScreenRecording
- (bool) enableScreenRecording
{
#if __clang_major__ >= 13 && MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_VERSION_12_3
if (@available(macOS 12.3, *)) {
@ -192,7 +194,7 @@
dispatch_semaphore_t sema = dispatch_semaphore_create(0);
// Attempt to use SCShareableContent to check for screen recording permission
[SCShareableContent getShareableContentWithCompletionHandler:^(SCShareableContent * _Nullable content,
[SCShareableContent getShareableContentWithCompletionHandler:^(SCShareableContent * _Nullable content,
NSError * _Nullable error) {
Q_UNUSED(error);
if (content) {
@ -231,8 +233,29 @@
[window setSharingType: state ? NSWindowSharingNone : NSWindowSharingReadOnly];
}
- (void) configureWindowAndHelpMenus:(QMainWindow*) mainWindow helpMenu:(QMenu*) helpMenu
{
QMenu *qtWindowMenu = new QMenu(AppKit::tr("Window"));
NSMenu *nsWindowMenu = qtWindowMenu->toNSMenu();
QString minimizeStr = AppKit::tr("Minimize");
[nsWindowMenu addItemWithTitle:minimizeStr.toNSString() action:@selector(performMiniaturize:) keyEquivalent:@""];
QString zoomStr = AppKit::tr("Zoom");
[nsWindowMenu addItemWithTitle:zoomStr.toNSString() action:@selector(performZoom:) keyEquivalent:@""];
[nsWindowMenu addItem:[NSMenuItem separatorItem]];
QString bringAllToFrontStr = AppKit::tr("Bring All to Front");
[nsWindowMenu addItemWithTitle:bringAllToFrontStr.toNSString() action:@selector(arrangeInFront:) keyEquivalent:@""];
NSApp.windowsMenu = nsWindowMenu;
mainWindow->menuBar()->insertMenu(helpMenu->menuAction(), qtWindowMenu);
NSApp.helpMenu = helpMenu->toNSMenu();
}
@end
//
// ------------------------- C++ Trampolines -------------------------
//
@ -312,3 +335,8 @@ void AppKit::setWindowSecurity(QWindow* window, bool state)
auto view = reinterpret_cast<NSView*>(window->winId());
[static_cast<id>(self) setWindowSecurity:view.window state:state];
}
void AppKit::configureWindowAndHelpMenus(QMainWindow* window, QMenu* helpMenu)
{
[static_cast<id>(self) configureWindowAndHelpMenus:window helpMenu:helpMenu];
}

View file

@ -24,6 +24,7 @@
#include <QStandardPaths>
#include <QTimer>
#include <QWindow>
#include <QMenu>
#include <ApplicationServices/ApplicationServices.h>
@ -202,6 +203,11 @@ void MacUtils::registerNativeEventFilter()
::InstallApplicationEventHandler(MacUtils::hotkeyHandler, 1, &eventSpec, this, nullptr);
}
void MacUtils::configureWindowAndHelpMenus(QMainWindow* mainWindow, QMenu* helpMenu)
{
return m_appkit->configureWindowAndHelpMenus(mainWindow, helpMenu);
}
bool MacUtils::registerGlobalShortcut(const QString& name, Qt::Key key, Qt::KeyboardModifiers modifiers, QString* error)
{
auto keycode = qtToNativeKeyCode(key);

View file

@ -54,6 +54,8 @@ public:
void registerNativeEventFilter() override;
void configureWindowAndHelpMenus(QMainWindow* mainWindow, QMenu* helpMenu);
bool registerGlobalShortcut(const QString& name,
Qt::Key key,
Qt::KeyboardModifiers modifiers,