溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務(wù)條款》

Qt6中如何實現(xiàn)QtMultimedia多媒體模塊

發(fā)布時間:2021-09-01 13:42:06 來源:億速云 閱讀:346 作者:小新 欄目:開發(fā)技術(shù)

這篇文章給大家分享的是有關(guān)Qt6中如何實現(xiàn)QtMultimedia多媒體模塊的內(nèi)容。小編覺得挺實用的,因此分享給大家做個參考,一起跟隨小編過來看看吧。

    一、前言

    Qt 6.2 的第一個測試版剛剛發(fā)布,并在多個其他新附加組件中加入了全新的 Qt 多媒體模塊。Qt Multimedia 是一個模塊,它在 Qt 6 中發(fā)生了一些相當(dāng)大的變化。

    在很多方面,它是一個新的 API 和實現(xiàn),即使我們重新使用了 Qt 5.15 中的一些代碼。雖然我們試圖為我們的大多數(shù)模塊保持 Qt 5 和 Qt 6 之間盡可能多的源代碼兼容性,但我們不得不在此處進行大量更改以使 API 和實現(xiàn)適合未來,最終決定以最好的為目標(biāo)API 而不是最大的兼容性。

    如果您一直在 Qt 5 中使用 Qt Multimedia,則需要對您的實現(xiàn)進行更改。將嘗試引導(dǎo)您完成最大的變化,同時查看 API 和內(nèi)部結(jié)構(gòu)。

    二、目標(biāo)

    Qt 5 中的 Qt 多媒體有一個相當(dāng)松散定義的范圍。不同后端對 API 不同部分的支持并不一致,而且 API 本身的部分也不容易跨平臺使用。

    對于 Qt 6,我們嘗試在一定程度上縮小范圍,并致力于開發(fā)一組一致的功能,這些功能適用于所有支持的平臺。我們還沒有達到這個目標(biāo),但希望通過 Qt 6.2.0 的發(fā)布填補大部分實施空白。

    據(jù)我們所知,這些功能涵蓋了我們用戶過去使用 Qt 多媒體的大部分用例。我們的目標(biāo)是首先關(guān)注那些核心用例,并確保它們在我們的所有平臺上一致工作,然后再使用新功能擴展模塊。

    我們希望在 Qt 6.2 中支持的主要用例是:

    • 音頻和視頻播放

    • 音頻和視頻錄制(來自相機和麥克風(fēng))

    • 低級(基于 PCM)音頻和音頻解碼

    • 與 Qt Quick 和小部件集成

    • 盡量使用硬件加速

    三、內(nèi)部架構(gòu)變化

    • Qt 5 中的 Qt 多媒體具有復(fù)雜的基于插件的架構(gòu),使用多個插件來實現(xiàn)不同的前端功能。一個完整的多媒體后端實現(xiàn)將包含不少于 4 個插件。用于實現(xiàn)這些插件的后端 API 是公開的,很難調(diào)整和改進這些后端的功能。

    • 構(gòu)建的架構(gòu)非常難以維護和開發(fā)模塊。在 Qt6 中,我們選擇顯著簡化這一過程并移除插件基礎(chǔ)設(shè)施?,F(xiàn)在在編譯時選擇后端并編譯到 Qt Multimedia 的共享庫中?,F(xiàn)在只有一個后端 API 涵蓋了所有多媒體,消除了我們在 Qt 5 中人為拆分成多個后端的問題。最后,我們選擇將后端 API 設(shè)為私有,以便我們將來可以輕松調(diào)整和擴展它。

    • 完成后,我們可以仔細查看平臺相關(guān)后端代碼所需的 API 和接口。我們設(shè)法將實現(xiàn)多媒體后端所需的類集從 40 個減少到 15 個,并減少了純虛擬方法的數(shù)量,為許多非必要功能提供了后備實現(xiàn)。

    • 新的后端 API 在某種程度上模仿了我們在 Qt Gui 中用于窗口系統(tǒng)集成的 QPA 架構(gòu),并且新的QPlatformMediaIntegration類現(xiàn)在確實作為一個通用的入口點和工廠類來實例化平臺相關(guān)的后端對象。在大多數(shù)情況下,我們現(xiàn)在的目標(biāo)是在公共 API 中的類和實現(xiàn)該功能的類之間建立一對一的關(guān)系。因此,公共QMediaPlayer API 有一個QPlatformMediaPlayer類實現(xiàn)平臺相關(guān)功能。

    • 通過這些更改,我們還可以刪除大量在前端和后端之間重復(fù)的代碼,并避免它們之間的大量呼叫轉(zhuǎn)移。有了這個,我們還可以將許多跨平臺功能和驗證移到代碼的共享、平臺獨立部分中。

    • 總而言之,這極大地簡化了我們的代碼庫,并在不丟失大量功能的情況下大大減少了代碼大小。5.15 中的 Qt Multimedia 大約有 140.000 行代碼,而我們目前在 Qt 6 中減少到大約 74.000 行代碼。

    四、支持的后端

    • 在 Qt 6 中,我們還重新審視了支持的后端,并將其縮減為我們認為將來可以支持的一組。例如,在 Qt 5 中,我們在 Windows 上有三個完全不同的后端實現(xiàn),使用 DirectShow、WMF 和一個單獨的基于 WMF 的 WinRT 實現(xiàn)。

    • Qt 6.3 計劃支持 QNX。我們可能還會在 6.2 中及時在 WebAssembly 上使用低級音頻。此外,我們?nèi)杂惺褂?PulseAudio 或 ALSA 在 Linux 上支持低級音頻的代碼,但目前尚未測試或支持這些代碼。根據(jù)需求,我們可能會在以后的版本中將它們帶回來。

    在 Qt 6 中,當(dāng)前支持的集合是:

    • Linux,使用 GStreamer

    • 使用 AVFoundation 的 macOS 和 iOS

    • 使用 WMF 的 Windows

    • 使用 MediaPlayer 和 Camera Java API 的 Android

    五、公共API接口

    Qt Multimedia的公共 API由 5 個大型功能塊組成。其中三個塊已經(jīng)存在于 Qt 5 中,但是這些塊中的 API 發(fā)生了重大變化。功能塊是:

    • 設(shè)備發(fā)現(xiàn)

    • 低電平音頻

    • 播放和解碼

    • 捕獲和記錄

    • 視頻輸出管道

    在做新的 API 的時候,我們也希望在 C++ 和 QML 之間有一個統(tǒng)一的 API。這使我們可以刪除大量代碼,這些代碼只是簡單地包裝了 C++ API 并以稍微不同的方式將其暴露給 QML。對于大多數(shù)公共 C++ 類,現(xiàn)在有一個相應(yīng)的同名 QML 項。所以QMediaPlayer并例如具有相應(yīng)QML MediaPlayer的具有相同的API作為C ++類的項目。

    (一)設(shè)備發(fā)現(xiàn)

    讓我們從設(shè)備發(fā)現(xiàn)開始。新的QMediaDevices 類旨在為您提供有關(guān)可用音頻和視頻設(shè)備的信息。它將允許您列出可用的音頻輸入(通常是麥克風(fēng))、音頻輸出(揚聲器和耳機)和攝像頭。您可以檢索默認設(shè)備,類還會通知您有關(guān)配置的任何更改,例如,當(dāng)用戶連接外部耳機時。

    QMediaDevices devices;
    connect(&devices, &QMediaDevices::audioInputsChanged, 
            []() { qDebug() << “available audio inputs have changed”; }

    (二)低電平音頻

    此功能塊有助于使用原始 PCM 數(shù)據(jù)處理低電平音頻,并直接從音頻設(shè)備讀取或?qū)懭朐摂?shù)據(jù)。

    • 這個塊在架構(gòu)上仍然與我們在 Qt 5 中的非常相似,但很多細節(jié)都發(fā)生了變化。最值得注意的是,讀取或?qū)懭胍纛l設(shè)備的低級類已更改名稱。它們現(xiàn)在稱為QAudioSource 和QAudioSink。命名反映了它們的低級性質(zhì),并釋放了我們在 Qt 5 中的舊名稱(QAudioInput和QAudioOutput)以用于播放和捕獲 API。

    • 所述QAudioFormat API已被清理和簡化,現(xiàn)在支撐4最常用的PCM數(shù)據(jù)格式(8位無符號整型,16和32位有符號整數(shù)和浮點數(shù)據(jù))。QAudioFormat還獲得了新的 API 來處理音頻通道的定位信息,但目前后端尚未完全支持。

    • 我們還刪除了已棄用的QSound類。QSoundEffect是它以低延遲播放短聲音的替代品。QSoundEffect目前仍要求您使用 WAV 作為效果格式,但我們計劃擴展此格式,并允許在 6.2 之后通過類播放壓縮的音頻數(shù)據(jù)。

    (三)回放

    處理媒體文件播放的主要類是QMediaPlayer。該QMediaPlayer API已經(jīng)從我們在Qt5簡化了我們必須從現(xiàn)在模塊去掉了所有的播放列表功能,這在過去是內(nèi)置了Qt 5媒體播放器,但其復(fù)雜的API和實現(xiàn)。我們計劃在 6.2 之后將播放列表功能作為一個單獨的獨立類帶回來,然后您可以在需要時連接到QMediaPlayer?,F(xiàn)在,如果需要,您可以在“播放器”示例中找到一些處理播放列表的代碼。

    另一方面,QMediaPlayer獲得了渲染字幕的能力,您現(xiàn)在可以使用setActiveAudioTrack()、setActiveVideoTrack()和setActiveSubtitleTrack()方法檢查和選擇所需的音頻、視頻或字幕軌道。

    Qt 6 中的 QMediaPlayer 要求您使用setAudioOutput()和setVideoOutput()方法將其主動連接到音頻和視頻輸出。不設(shè)置音頻輸出將意味著媒體播放器不播放音頻。這是對 Qt 5 的更改,在 Qt 5 中始終選擇默認音頻輸出。進行了更改以允許音頻和視頻之間的對稱 API 并簡化與 QML 的集成

    除了QMediaPlayer 之外,Qt 6 還具有跨平臺支持,可以使用QAudioDecoder類將音頻文件解碼為原始 PCM 數(shù)據(jù)。該功能存在于 Qt 5 的某些平臺上,但并未在所有平臺上實現(xiàn)。

    用 C++ 實現(xiàn)的最小媒體播放器如下所示:

    //widget示例
    QMediaPlayer player;
    QAudioOutput audioOutput; // chooses the default audio routing
    player.setAudioOutput(&audioOutput);
    QVideoWidget *videoOutput = new QVideoWidget;
    player.setVideoOutput(videoOutput);
    player.setSource(“mymediafile.mp4”);
    player.play();
    
    //qml示例
    Window {
        MediaPlayer {
            id: mediaPlayer
            audioOutput: AudioOutput {} // use default audio routing
            videoOutput: videoOutput
            source: “mymediafile.mp4”
        }
    
        VideoOutput {
            id: videoOutput
            anchors.fill: parent
        }
    
        Component.onCompleted: mediaPlayer.play()
    }

    (四)捕獲和記錄

    捕獲和記錄功能在 Qt 6 中經(jīng)歷了最大的 API 更改。在 Qt 5 中,您必須神奇地將相機連接到記錄器,而 Qt 6 現(xiàn)在帶有更明確的 API 來設(shè)置捕獲管道。

    Qt 6 中的中心類是QMediaCaptureSession。錄制音頻/視頻或捕獲圖像時始終需要此類。要設(shè)置錄音會話,您可以使用setAudioInput()將音頻輸入連接到會話,如果您想從相機錄制,請使用setCamera()將相機連接到它。

    這里要注意的一件事是QAudioInput和QCamera充當(dāng)兩個輸入通道。使用QAudioInput::setDevice()或QCamera::setCameraDevice()選擇要使用的物理設(shè)備。選擇設(shè)備后,QAudioInput和QCamera允許您更改該設(shè)備的屬性,例如設(shè)置音量或相機的分辨率和幀速率。

    QMediaCaptureSession允許將音頻和視頻輸出連接到它以進行預(yù)覽和監(jiān)視。要拍攝靜止圖像,請使用setImageCapture()將QImageCapture對象連接到它。

    要錄制音頻和視頻,請將QMediaRecorder連接到會話。QMediaRecorder允許通過指定一個請求記錄特定的文件格式和編解碼器QMediaFormat。在 Qt 6 中,我們沒有在此處提供跨平臺 API,使用不同格式和編解碼器的枚舉。

    由于編解碼器支持取決于平臺,您還可以查詢QMediaFormat以獲取支持的文件格式和編解碼器集。后端也將始終嘗試將請求的格式解析為支持的格式。

    因此,例如,如果您請求帶有 H265 視頻編解碼器的 MPEG4 文件,但不支持 H265,則它可能會回退到 H264 或其他受支持的編解碼器。

    除了設(shè)置格式之外,您還可以在編碼器上設(shè)置其他屬性,例如質(zhì)量、分辨率和幀率。

    QMediaCaptureSession session;
    QCamera camera;
    session.addCamera(&camera);
    QImageCapture imageCapture;
    session.addImageCapture(&imageCapture);
    camera.start();
    imageCapture.captureToFile(“myimage.jpg”);
    
    QMediaRecorder recorder;
    session.setRecorder(&recorder);
    
    QMediaFormat format(QMediaFormat::MPEG4);
    format.setAudioCodec(QMediaFormat::AudioCodec::AAC);
    format.setVideoCodec(QMediaFormat::VideoCodec::H265);
    recorder.setMediaFormat(format);
    
    recorder.setOutputLocation(“mycapture.mp4”);
    recorder.record();

    (五)視頻管道

    • 視頻管道已使用 Qt 6 完全重寫,試圖使其更易于用于自定義用例,并允許解碼和渲染的完整硬件加速以及在軟件中接收原始視頻數(shù)據(jù)。

    • 這個 API 的大部分只能從 C++ 訪問,在 QML 端,有一個VideoOutput QML 元素,但是可以很容易地連接到著色器效果之類的東西,或者可以用作 Qt Quick 3D 中材質(zhì)的 sourceItem。

    • 如果您使用 Qt Widgets,則QVideoWidget類可用作那里視頻的輸出表面。

    • 對于更底層的訪問,C++ 端的中心類是QVideoSink。QVideoSink可用于從媒體播放器或捕獲會話接收單個視頻幀。 然后可以將單個QVideoFrame對象映射到內(nèi)存中,用戶必須準(zhǔn)備好處理各種 YUV 和 RGB 格式,可以使用QPainter渲染或可以轉(zhuǎn)換為QImage。

    六、未來的工作

    在 6.2 之后,我們將研究待辦事項中的幾個項目。這些想法的優(yōu)先級尚未完成,關(guān)于您的需求的反饋將在這里幫助我們。我們的想法包括:

    • 支持多視頻輸出

    • 支持多攝像頭

    • 支持多個音頻輸入

    • 流媒體音頻/視頻

    • 截屏

    • 音頻混合

    然而,目前,我們的大部分工作都集中在錯誤修復(fù)和為 Qt 6.2 做好一切準(zhǔn)備上。由于較大的變化,在實現(xiàn)中仍然存在許多粗糙的邊緣,并且某些功能可能存在錯誤或缺少功能。我們的目標(biāo)是在 6.2.0 中修復(fù)這些問題,但需要您的反饋才能這樣做。

    最近發(fā)布的 Qt 6.2 測試版確實有 Qt 多媒體的二進制文件,您可以輕松地嘗試和使用它們。我們非常感謝任何反饋,無論是在博客上還是在 bugreports.qt.io。

    感謝各位的閱讀!關(guān)于“Qt6中如何實現(xiàn)QtMultimedia多媒體模塊”這篇文章就分享到這里了,希望以上內(nèi)容可以對大家有一定的幫助,讓大家可以學(xué)到更多知識,如果覺得文章不錯,可以把它分享出去讓更多的人看到吧!

    向AI問一下細節(jié)

    免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點不代表本網(wǎng)站立場,如果涉及侵權(quán)請聯(lián)系站長郵箱:is@yisu.com進行舉報,并提供相關(guān)證據(jù),一經(jīng)查實,將立刻刪除涉嫌侵權(quán)內(nèi)容。

    AI