iOS 視圖渲染數據轉CVPixelBuffer

来源:https://www.cnblogs.com/Unclefeng/archive/2019/08/28/11425460.html
-Advertisement-
Play Games

void *pxdata = CVPixelBufferGetBaseAddress(pxbuffer);然後在創建上下文以pxdata 所指向的記憶體作為上下文數據存貯的容器, 最後 渲染 上下文[self.webView.layer renderInContext:context];這樣就將 we ...


近兩年一直從事視頻行業的開發, 加班也比較嚴重, 好久沒有寫文章了, 最近稍微有些時間, 前來寫點文章, 記錄一些開發中遇到的問題, 和解決方法!
做視頻會議項目, 當然是離不開音視頻啦, 也常常和WebRTC打交道, 包括編譯WebRTC, 修改源碼, 還有C++和OC的混編開發, JS交互, 也嘗試過RN的開發來避開一些問題等等, 東西很多, 路也很不好走, 通宵加班也是家常便飯, 不過現在項目基本穩定,已經上線, 用戶反饋也都很不錯! 回頭看看走過的路, 雖然坎坎坷坷, 但是也是收穫滿滿呀!
進入正題, 項目中有共用的功能, 屏幕共用使用的ReplayKit, 但是應用外的屏幕共用時是使用的Broadcast Extension, 而該擴展是另外的獨立進程, 涉及到宿主App和擴展App的信令之間的交互, 好在有比較有好的第三方使用, 省了不少事, 最終完成了屏幕共用! 如果有朋友涉及到這方面的知識的話, 可以一起交流溝通哈!
除屏幕共用外, 我們要有網頁共用, 網頁共用, 開始一臉懵逼! 後來的解決方案是, 共用人端使用WKWebView, 觀看端看的是視頻流! OK, 那麼問題來了, 如何把一個UIView 的渲染數據採集成為Buffer呢, 頭大, 最初考路過使用應用內的錄屏, 這樣是可以解決, 但是, 錄屏的話吧整個屏幕上的內容全都採集出來, 不是很友好, 用戶只想共用這個網頁, 其他的不想讓觀看者看到! 確實挺麻煩的, 查了很多資料, 也沒有特別合適的!
經過多方面研究和資料的查閱, 最終的解決方案是, 創建CVPixelBufferRef pxbuffer, 然後獲取像素基本地址

void *pxdata = CVPixelBufferGetBaseAddress(pxbuffer);
然後在創建上下文以pxdata 所指向的記憶體作為上下文數據存貯的容器, 最後 渲染 上下文[self.webView.layer renderInContext:context];
這樣就將 webView 視圖上的渲染數據轉成了一幀 CVPixelBufferRef 數據, 然後根據幀率設置定時器, 去不停的獲取webView的渲染數據轉換成需要像素緩衝數據!

具體的代碼如下

- (CVPixelBufferRef)CVPixelBufferRef {
    
    CGSize size = self.frame.size;
    NSDictionary *options = @{(NSString*)kCVPixelBufferCGImageCompatibilityKey : @YES,
                              (NSString*)kCVPixelBufferCGBitmapContextCompatibilityKey : @YES,
                              (NSString*)kCVPixelBufferIOSurfacePropertiesKey: [NSDictionary dictionary]};
    CVPixelBufferRef pxbuffer = NULL;
    
    CGFloat frameWidth = size.width;
    CGFloat frameHeight = size.height;
    
    CVReturn status = CVPixelBufferCreate(kCFAllocatorDefault,
                                          frameWidth,
                                          frameHeight,
                                          kCVPixelFormatType_32ARGB,
                                          (__bridge CFDictionaryRef) options,
                                          &pxbuffer);
    
    NSParameterAssert(status == kCVReturnSuccess && pxbuffer != NULL);
    
    CVPixelBufferLockBaseAddress(pxbuffer, 0);
    void *pxdata = CVPixelBufferGetBaseAddress(pxbuffer);
    NSParameterAssert(pxdata != NULL);
    
    CGColorSpaceRef rgbColorSpace = CGColorSpaceCreateDeviceRGB();
    
    CGContextRef context = CGBitmapContextCreate(pxdata, size.width, size.height, 8, CVPixelBufferGetBytesPerRow(pxbuffer), rgbColorSpace, kCGImageAlphaPremultipliedFirst);
    
    NSParameterAssert(context);
    
    CGContextConcatCTM(context, CGAffineTransformMakeRotation(0));
    CGAffineTransform flipVertical = CGAffineTransformMake( 1, 0, 0, -1, 0, frameHeight);
    CGContextConcatCTM(context, flipVertical);
    
//    CGAffineTransform flipHorizontal = CGAffineTransformMake( -1.0, 0.0, 0.0, 1.0, frameWidth, 0.0 );
//    CGContextConcatCTM(context, flipHorizontal);


    [self.webView.layer renderInContext:context];
    
    CGColorSpaceRelease(rgbColorSpace);
    CGContextRelease(context);
    CVPixelBufferUnlockBaseAddress(pxbuffer, 0);
    
    return pxbuffer;
}

 

 這或許不是最好的方法, 但目前確實解決了燃眉之急, 分享出來, 為有同樣需求的小伙伴提供一條方案, 或者小伙伴有更好的方法, 分享出來, 大家可以學習交流一下

或者上我的簡書

 


您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • flink是一款開源的大數據流式處理框架,他可以同時批處理和流處理,具有容錯性、高吞吐、低延遲等優勢,本文簡述flink在windows和linux中安裝步驟,和示常式序的運行。 首先要想運行Flink,我們需要下載並解壓Flink的二進位包,下載地址如下:https://flink.apache. ...
  • 四、簡單查詢 ​ 簡單查詢的主要特征就是將一張數據表之中的全部數據行進行顯示,而後可以利用 SELECT 子句來控制所需要的輸出列。 4.1、基礎語法 範例 :查詢 emp 表中的數據(全部數據查詢) ​ 在取得全部數據後,可以發現某些列上會顯示 null 的信息,null 表示的是沒有內容,但 n ...
  • 在資料庫view的創建中,會遇到一些跨資料庫的view腳本,但是在將view更新到production的時候可能忘記更改database name,導致出現一些問題。 以下腳本可以檢查出包含某個關鍵字的view name,只需要修改 條件即可 TSql type(v,fn,p) select nam ...
  • [學習筆記] 3)配置環境變數:(環境變數中的~1,~2,~3的用法)i)JAVA_HOME:註意C:\Program Files目錄存在空格,變成C:\Progra~1\Java\jdk1.8.0_144。(註意:長於8個字元的文件名和文件夾名,都被簡化成前面6個有效字元,後面~1,有重名的就 ~ ...
  • 1. 簡介 資料庫,現代化的數據存儲存儲手段,是一種特殊的文件,其中存儲著需要的數據。 特點: 持久化存儲 讀寫速度極高 保證數據的有效性 對程式支持性非常好,容易擴展 2. Mysql (1)具有數據完整性: 一個資料庫就是一個完整的業務單元,可以包含多張表,數據被存儲在表中。在表中為了更加準確的 ...
  • 設置主機名 [root@localhost ~]# cat /etc/hosts127.0.0.1 localhost localhost.localdomain localhost4 localhost4.localdomain4::1 localhost localhost.localdomai... ...
  • 前言 最近在處理一個歷史遺留項目的時候飽受其害,主要表現為偶發性的 SharedPreferences 配置文件數據錯亂,甚至丟失。經過排查發現是多進程的問題。項目中有兩個不同進程,且會頻繁的讀寫 SharedPreferences 文件,所以導致了數據錯亂和丟失。趁此機會,精讀了一遍 Shared ...
  • 本篇概要 小程式開發前的準備 小程式視圖與渲染 小程式事件 註:總的來說,微信小程式的開發代碼寫法,和 HTML、CSS、JavaScript類似很像.jpg 一,微信小程式開發前的準備 於微信小程式官網進行註冊 ==> https://mp.weixin.qq.com/cgi-bin/wx 註冊完 ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...