Fix WinRT apartment initialization crash

Handle case where COM/WinRT apartment is already initialized by Qt or other components. Track whether we initialized the apartment to avoid uninitializing it if we didn't initialize it.

Co-authored-by: jonaski <10343810+jonaski@users.noreply.github.com>
This commit is contained in:
copilot-swe-agent[bot]
2025-12-28 19:31:43 +00:00
parent 597f983c92
commit 02c1596ff4
2 changed files with 19 additions and 4 deletions

View File

@@ -68,11 +68,22 @@ WindowsMediaController::WindowsMediaController(HWND hwnd,
player_(player),
playlist_manager_(playlist_manager),
current_albumcover_loader_(current_albumcover_loader),
smtc_(nullptr) {
smtc_(nullptr),
apartment_initialized_(false) {
try {
// Initialize WinRT
winrt::init_apartment();
// Initialize WinRT apartment if not already initialized
// Qt or other components may have already initialized it
try {
winrt::init_apartment(winrt::apartment_type::single_threaded);
apartment_initialized_ = true;
}
catch (const hresult_error &e) {
// Apartment already initialized - this is fine, continue
if (e.code() != RPC_E_CHANGED_MODE) {
throw;
}
}
// Create private implementation
auto *priv = new WindowsMediaControllerPrivate();
@@ -153,7 +164,10 @@ WindowsMediaController::~WindowsMediaController() {
delete priv;
smtc_ = nullptr;
}
winrt::uninit_apartment();
// Only uninit if we initialized the apartment
if (apartment_initialized_) {
winrt::uninit_apartment();
}
}
void WindowsMediaController::SetupButtonHandlers() {

View File

@@ -63,6 +63,7 @@ class WindowsMediaController : public QObject {
const SharedPtr<CurrentAlbumCoverLoader> current_albumcover_loader_;
void *smtc_; // Pointer to SystemMediaTransportControls (opaque to avoid WinRT headers in public header)
QString current_song_art_url_;
bool apartment_initialized_; // Track if we initialized the WinRT apartment
};
#endif // WINDOWSMEDIACONTROLLER_H