真实的国产乱ⅩXXX66竹夫人,五月香六月婷婷激情综合,亚洲日本VA一区二区三区,亚洲精品一区二区三区麻豆

成都創(chuàng)新互聯(lián)網(wǎng)站制作重慶分公司

flutter混合優(yōu)化,flutter 列表優(yōu)化

Flutter -Listview 4個(gè)優(yōu)化能讓你的列表絲般順滑

優(yōu)化點(diǎn)1:使用 builder構(gòu)建列表

成都創(chuàng)新互聯(lián)公司是一家集網(wǎng)站建設(shè),垣曲企業(yè)網(wǎng)站建設(shè),垣曲品牌網(wǎng)站建設(shè),網(wǎng)站定制,垣曲網(wǎng)站建設(shè)報(bào)價(jià),網(wǎng)絡(luò)營銷,網(wǎng)絡(luò)優(yōu)化,垣曲網(wǎng)站推廣為一體的創(chuàng)新建站企業(yè),幫助傳統(tǒng)企業(yè)提升企業(yè)形象加強(qiáng)企業(yè)競(jìng)爭(zhēng)力。可充分滿足這一群體相比中小企業(yè)更為豐富、高端、多元的互聯(lián)網(wǎng)需求。同時(shí)我們時(shí)刻保持專業(yè)、時(shí)尚、前沿,時(shí)刻以成就客戶成長自我,堅(jiān)持不斷學(xué)習(xí)、思考、沉淀、凈化自己,讓我們?yōu)楦嗟钠髽I(yè)打造出實(shí)用型網(wǎng)站。

當(dāng)你的列表元素是動(dòng)態(tài)增長的時(shí)候(比如上拉加載更多),請(qǐng)不要直接用children 的方式,一直往children 的數(shù)組增加組件,那樣會(huì)很糟糕。對(duì)于 ListView.builder 是按需構(gòu)建列表元素,也就是只有那些可見得元素才會(huì)調(diào)用itemBuilder 構(gòu)建元素,這樣對(duì)于大列表而言性能開銷自然會(huì)小很多。

優(yōu)化點(diǎn)2:禁用 addAutomaticKeepAlives 和 addRepaintBoundaries 特性

這兩個(gè)屬性都是為了優(yōu)化滾動(dòng)過程中的用戶體驗(yàn)的。

addAutomaticKeepAlives 特性默認(rèn)是 true,意思是在列表元素不可見后可以保持元素的狀態(tài),從而在再次出現(xiàn)在屏幕的時(shí)候能夠快速構(gòu)建。這其實(shí)是一個(gè)拿空間換時(shí)間的方法,會(huì)造成一定程度得內(nèi)存開銷??梢栽O(shè)置為 false 關(guān)閉這一特性。缺點(diǎn)是滑動(dòng)過快的時(shí)候可能會(huì)出現(xiàn)短暫的白屏(實(shí)際會(huì)很少發(fā)生)。

addRepaintBoundaries 是將列表元素使用一個(gè)重繪邊界(Repaint Boundary)包裹,從而使得滾動(dòng)的時(shí)候可以避免重繪。而如果列表很容易繪制(列表元素布局比較簡單的情況下)的時(shí)候,可以關(guān)閉這個(gè)特性來提高滾動(dòng)的流暢度。

優(yōu)化點(diǎn)3:盡可能將列表元素中不變的組件使用 const 修飾

使用 const 相當(dāng)于將元素緩存起來實(shí)現(xiàn)共用,若列表元素某些部分一直保持不變,那么可以使用 const 修飾。

優(yōu)化點(diǎn)4:使用 itemExtent 確定列表元素滾動(dòng)方向的尺寸

對(duì)于很多列表,我們?cè)跐L動(dòng)方向上的尺寸是提前可以根據(jù) UI設(shè)計(jì)稿知道的,如果能夠知道的話,那么使用 itemExtent 屬性制定列表元素在滾動(dòng)方向的尺寸,可以提升性能。這是因?yàn)椋绻恢付ǖ脑?,在滾動(dòng)過程中,會(huì)需要推算每個(gè)元素在滾動(dòng)方向的尺寸從而消耗計(jì)算資源。

Flutter ListView 的4個(gè)優(yōu)化要點(diǎn),非常實(shí)用哦!實(shí)際上,這些要點(diǎn)都可以從官網(wǎng)的文檔里找出對(duì)應(yīng)得說明。因此,如果遇到了性能問題,除了搜索引擎外,也建議多看看官方的文檔。

Flutter性能優(yōu)化

1.圓角對(duì)性能的影響

盡量避免用Clipxxx組件,建議用BoxDecoration的image屬性實(shí)現(xiàn),如果用Clipxxx組件,圓角取整后性能會(huì)提升。

2.減少重繪

根據(jù)場(chǎng)景合理使用RePaintBoundary,使繪制獨(dú)立于父布局,避免重繪,提升性能,但過度使用增加的圖層會(huì)帶來Raster合成的耗時(shí)。例如scrollview是滑動(dòng)過程會(huì)導(dǎo)致所有的節(jié)點(diǎn)都重繪,可以在scrollview下一層使用RePaintBoundary。

3.滾動(dòng)步長插值器優(yōu)化(了解)

官方的滾動(dòng)差值器在出現(xiàn)小卡頓時(shí),滾動(dòng)步長會(huì)出現(xiàn)大的跳躍,導(dǎo)致體感上出現(xiàn)很明顯的抖動(dòng),優(yōu)化步長偏移量算法與原生效果對(duì)齊。

4.開啟SurfaceView

官方推薦Flutter用SurfaceView ,因?yàn)镾urfaceView與應(yīng)用窗口內(nèi)容分隔開,在專有硬件中合成,產(chǎn)生的中間副本少于TextureView,所以性能高,占用內(nèi)存少,但是在混合棧遇到的問題需要突破

5.使用RepaintBoundary 提升頻繁重繪控件的性能。使用RelayoutBoundary提升頻繁修改大小,增刪的布局中也可以提升性能。

6.build中不要去寫大量的耗時(shí)邏輯,因?yàn)閿?shù)據(jù)更新會(huì)觸發(fā)build的多次調(diào)用,在里面做耗時(shí)邏輯會(huì)降低性能。

7.盡量使用statelessWidget代替statefulWidget,因?yàn)閟tatefulWidget的銷毀重建會(huì)引起子widget的銷毀與重建。

8.解析json可以放到子線程線程中,開Isolate去解析,這樣,當(dāng)返回?cái)?shù)據(jù)特別大的時(shí)候也不會(huì)阻塞界面。

9.使用不變的組件的時(shí)候可以添加const,const組件不會(huì)進(jìn)行build更新

10.由于flutter通過widget.runtimeType和key來判斷是否需要跟新組建,所以我們寫組件的時(shí)候盡量保持key不變,或者不寫key。對(duì)于一些需要頻繁改變,例如新增、刪除、排序的最好加上key。如果type一直,如果不寫key容易導(dǎo)致,element無法區(qū)分新舊widget,導(dǎo)致無法更新。

Flutter(六)Android與Flutter混合開發(fā)(Hybird)

如果我們目前的項(xiàng)目是Android的,但是接下來我們希望部分頁面可以使用Flutter進(jìn)行開發(fā),甚至我們希望在Native頁面中嵌入FlutterUI組件,那么我們?cè)撊绾螌?shí)現(xiàn)呢?

假設(shè)你現(xiàn)在Android項(xiàng)目的目錄的結(jié)構(gòu)是這樣的

這時(shí)候如果你想創(chuàng)建一個(gè)Flutter模塊,使得Android模塊和Flutter模塊之間可以進(jìn)行交互,我們可以通過Android Studio新建一個(gè)Flutter Module,具體過程是:File — New — New Module ,之后選擇Flutter Module,指定Project Location的路徑為

也就是說,最終你的項(xiàng)目結(jié)構(gòu)會(huì)是這樣的

接下來在Android Module的 build.gradle 文件中添加flutter依賴

先創(chuàng)建一個(gè)Flutter頁面

這里比較重要的是 window.defaultRouteName 這個(gè)字段,這個(gè)字段可以接收從Native傳遞過來的參數(shù) (下文我們會(huì)介紹原生傳遞參數(shù)的方法),也就是說通過這個(gè)字段我們就可以進(jìn)行Flutter頁面的路由的分發(fā)

我們可以直接在Android的 MainActivity 中啟動(dòng)一個(gè) FlutterActivity ,這里的 initialRoute 方法中傳遞的參數(shù)就對(duì)應(yīng)Flutter層的 window.defaultRouteName

注意:需要在 AndroidManifest.xml 注冊(cè) FlutterActivity

自己創(chuàng)建一個(gè) FlutterAppActivity 繼承自 FlutterActivity

在 MainActivity 中啟動(dòng) FlutterAppActivity (另外別忘了在 AndroidManifest.xml 中注冊(cè) FlutterAppActivity )

兩種啟動(dòng)方式的區(qū)別

如果單純只是想打開一個(gè)Flutter頁面,兩種方式實(shí)際上基本沒有太大區(qū)別,第一種方式也許還會(huì)更簡單一點(diǎn)。但是,在Flutter開發(fā)中,我們往往還需要開發(fā)一些Native插件供Flutter調(diào)用,如果使用復(fù)寫 FlutterActivity 的方式更有利于我們?cè)?FlutterActivity 中注冊(cè)我們的Native插件,所以實(shí)際開發(fā)中一般推薦使用第二種方式

擴(kuò)展思考

initialRoute 從名稱上看起來是Flutter提供給我們進(jìn)行Native與Flutter交互的路由跳轉(zhuǎn)的,但是實(shí)際上他就是一個(gè)字符串,我們不僅僅可以傳遞一個(gè)路由名稱,有時(shí)候我們也可以通過這個(gè)參數(shù)傳遞一串JSON數(shù)據(jù),然后在Flutter端進(jìn)行解析,這樣我們就可以通過這個(gè)參數(shù)做更多的事情

activity_main.xml

FrameLayout 用于承載Flutter組件

MainActivity.java

使用 FragmentManager 將 FlutterFragment 添加到 FrameLayout 容器中

運(yùn)行結(jié)果

上半部分是原生的TextView,下半部分是Flutter的Text組件

本節(jié)主要介紹了Native和Flutter之間的頁面跳轉(zhuǎn),以及同一個(gè)頁面中Native與Flutter組件的組合。接下來會(huì)介紹如何編寫Android插件與Flutter進(jìn)行數(shù)據(jù)交互

Flutter浪潮下的音視頻研發(fā)探索

文/陳爐軍

整理/LiveVideoStack

大家好,我是阿里巴巴閑魚事業(yè)部的陳爐軍,本次分享的主題是Flutter浪潮下的音視頻研發(fā)探索,主要內(nèi)容是針對(duì)閑魚APP在當(dāng)下流行的跨平臺(tái)框架Flutter的大規(guī)模實(shí)踐,介紹其在音視頻領(lǐng)域碰到的一些困難以及解決方案。

分享內(nèi)容主要分為四個(gè)方面,首先會(huì)對(duì)Flutter有一個(gè)簡單介紹以及選擇Flutter作為跨平臺(tái)框架的原因,其次會(huì)介紹Flutter中與音視頻關(guān)系非常大的外接紋理概念,以及對(duì)它做出的一些優(yōu)化。之后會(huì)對(duì)閑魚在音視頻實(shí)踐過程中碰到的一些Flutter問題提出了一些解決方案——TPM音視頻框架。最后是閑魚Flutter多媒體開源組件的介紹。

Flutter

Flutter是一個(gè)跨平臺(tái)框架,以往的做法是將音頻、視頻和網(wǎng)絡(luò)這些模塊都下沉到C++層或者ARM層,在其上封裝成一個(gè)音視頻的SDK,供UI層的PC、iOS和Android調(diào)用。

而Flutter做為一個(gè)UI層的跨平臺(tái)框架,顧名思義就是在UI層也實(shí)現(xiàn)了一個(gè)跨平臺(tái)開發(fā)??梢灶A(yù)想的是未Flutter發(fā)展的好的話,會(huì)逐漸變?yōu)橐粋€(gè)從底層到UI層的一個(gè)全鏈路的跨平臺(tái)開發(fā),技術(shù)人員分別負(fù)責(zé)SDK和UI層的開發(fā)。

在Flutter之前已經(jīng)有很多跨平臺(tái)UI解決方案,那為什么選擇Flutter呢?

我們主要考慮性能和跨平臺(tái)的能力。

以往的跨平臺(tái)方案比如Weex,ReactNative,Cordova等等因?yàn)榧軜?gòu)的原因無法滿足性能要求,尤其是在音視頻這種性能要求幾乎苛刻的場(chǎng)景。

而諸如Xamarin等,雖然性能可以和原生App一致,但是大部分邏輯還是需要分平臺(tái)實(shí)現(xiàn)。

我們可以看一下,為什么Flutter可以實(shí)現(xiàn)高性能:

原生的native組件渲染以IOS為例,蘋果的UIKit通過調(diào)用平臺(tái)自己的繪制框架QuaztCore來實(shí)現(xiàn)UI的繪制,圖形繪制也是調(diào)用底層的API,比如OpenGL、Metal等。

而Flutter也是和原生API邏輯一致,也是通過調(diào)用底層的繪制框架層SKIA實(shí)現(xiàn)UI層。這樣相當(dāng)于Flutter他自己實(shí)現(xiàn)了一套UI框架,提供了一種性能超越原生API的跨平臺(tái)可能性。

但是我們說一個(gè)框架最終性能怎樣,其實(shí)取決于設(shè)計(jì)者和開發(fā)者。至于現(xiàn)在到底是一個(gè)什么狀況:

在閑魚的實(shí)踐中,我們發(fā)現(xiàn)在正常的開發(fā)沒有特意的去優(yōu)化UI代碼的情況下,在一些低端機(jī)上,F(xiàn)lutter界面的流暢性是比Native界面要好的。

雖然現(xiàn)在閑魚某些場(chǎng)景下會(huì)有卡頓閃退等情況,但是這是一個(gè)新事物發(fā)展過程中的必然問題,我們相信未來性能肯定不會(huì)成為限制Flutter發(fā)展的瓶頸的。

在閑魚實(shí)踐Flutter的過程中,混合棧和音視頻是其中比較難解決的兩個(gè)問題,混合棧是指一個(gè)APP在Flutter過程中不可能一口氣將所有業(yè)務(wù)全部重寫為Flutter,所以這是一個(gè)逐步迭代的過程,這期間原生native界面與Flutter界面共存的狀態(tài)就稱之為混合棧。閑魚在混合棧上也有一些比較好的輸出,例如FlutterBoost。

外接紋理

在講音視頻之前需要簡要介紹一下外接紋理的概念,我們將它稱之為是Flutter和Frame之間的橋梁。

Flutter渲染一幀屏幕數(shù)據(jù)首先要做的是,GPU發(fā)出的VC信號(hào)在Flutter的UI線程,通過AOT編譯的機(jī)器碼結(jié)合當(dāng)前Dart Runtime,生成Layer Tree UI樹,Layer Tree上每一個(gè)葉子節(jié)點(diǎn)都代表了當(dāng)前屏幕上所需要渲染的每一個(gè)元素,包含了這些元素渲染所需要的內(nèi)容。將Layer Tree拋給GPU線程,在GPU線程內(nèi)調(diào)用Skia去完成整個(gè)UI的渲染過程。Layer Tree中有PictureLayer和TextureLayer兩個(gè)比較重要的節(jié)點(diǎn)。PictureLayer主要負(fù)責(zé)屏幕圖片的渲染,F(xiàn)lutter內(nèi)部實(shí)現(xiàn)了一套圖片解碼邏輯,在IO線程將圖片讀取或者從網(wǎng)絡(luò)上拉取之后,通過解碼能夠在IO線程上加載出紋理,交給GPU線程將圖片渲染到屏幕上。但是由于音視頻場(chǎng)景下系統(tǒng)API太過繁多,業(yè)務(wù)場(chǎng)景過于復(fù)雜。Flutter沒有一套邏輯去實(shí)現(xiàn)跨平臺(tái)的音視頻組件,所以說Flutter提出了一種讓第三方開發(fā)者來實(shí)現(xiàn)音視頻組件的方式,而這些音視頻組件的視頻渲染出口,就是TextureLayer。

在整個(gè)Layer Tree渲染的過程中,TextureLayer的數(shù)據(jù)紋理需要由外部第三方開發(fā)者來指定,可以把視頻數(shù)據(jù)和播放器數(shù)據(jù)送到TextureLayer里,由Flutter將這些數(shù)據(jù)渲染出來。

TextureLayer渲染過程:首先判斷Layer是否已經(jīng)初始化,如果沒有就創(chuàng)建一個(gè)Texture,然后將Texture Attach到一個(gè)SufaceTexture上。

這個(gè)SufaceTexture是音視頻的native代碼可以獲取到的對(duì)象,通過這個(gè)對(duì)象創(chuàng)建的Suface,我們可以將視頻數(shù)據(jù)、攝像頭數(shù)據(jù)解碼放到Suface中,然后Flutter端通過監(jiān)聽SufaceTexture的數(shù)據(jù)更新就可以順利把剛才創(chuàng)建的數(shù)據(jù)更新到它的紋理中,然后再將紋理交給SKIA渲染到屏幕上。

然而我們?nèi)绻枰肍lutter實(shí)現(xiàn)美顏,濾鏡,人臉貼圖等等功能,就需要將視頻數(shù)據(jù)讀取出來,更新到紋理中,再將GPU紋理經(jīng)過美顏濾鏡處理后生成一個(gè)處理后的紋理。按Flutter提供的現(xiàn)有能力,必須先將紋理中的數(shù)據(jù)從GPU讀出到CPU中,生成Bitmap后再寫入Surface中,這樣在Flutter中才能順利的更新到視頻數(shù)據(jù),這樣做對(duì)系統(tǒng)性能的消耗很大。

通過對(duì)Flutter渲染過程分析,我們知道Flutter底層需要渲染的數(shù)據(jù)就是GPU紋理,而我們經(jīng)過美顏濾鏡處理完成以后的結(jié)果也是GPU紋理,如果可以將它直接交給Flutter渲染,那就可以避免GPU-CPU-GPU這樣的無用循環(huán)。這樣的方法是可行的,但是需要一個(gè)條件,就是OpenGL上下文共享。

OpenGL

在說上下文之前,得提到一個(gè)和上線文息息相關(guān)的概念:線程。

Flutter引擎啟動(dòng)后會(huì)啟動(dòng)四個(gè)線程:

第一個(gè)線程是UI線程,這是Flutter自己定義的UI線程,主要負(fù)責(zé)GPU發(fā)出的VSync信號(hào)時(shí)候用當(dāng)前Dart編譯的機(jī)器碼和當(dāng)前運(yùn)行環(huán)境創(chuàng)建出Layer Tree。

還有就是IO線程和GPU線程。和大部分OpenGL處理解決方案中一樣,F(xiàn)lutter也采取一個(gè)線程責(zé)資源加載,一部分負(fù)責(zé)資源渲染這種思路。

兩個(gè)線程之間紋理共享有兩種方式。一種是EGLImage(IOS是 CVOpenGLESTextureCache)。一種是OpenGL Share Context。Flutter通過Share Context來實(shí)現(xiàn)紋理共享,將IO線程的Context和GPU線程的Context進(jìn)行Share,放到同一個(gè)Share Group下面,這樣兩個(gè)線程下資源是互相可見可以共享的。

Platform線程是主線程,F(xiàn)lutter中有一個(gè)很奇怪的設(shè)定,GPU線程和主線程共用一個(gè)Context。并且在主線程也有很多OpenGL 操作。

這樣的設(shè)計(jì)會(huì)給音視頻開發(fā)帶來很多問題,后面會(huì)詳細(xì)說。

音視頻端美顏處理完成的OpenGL紋理能夠讓Flutter直接使用的條件就是Flutter的上下文需要和平臺(tái)音視頻相關(guān)的OpenGL上下文處在一個(gè)Share Group下面。

由于Flutter主線程的Context就是GPU的Context,所以在音視頻端主線程中有一些OpenGL操作的話,很有可能使Flutter整個(gè)OpenGL被破壞掉。所以需要將所有的OpenGL操作都限制在子線程中。

通過上述這兩個(gè)條件的處理,我們就可以在沒有增加GPU消耗的前提下實(shí)現(xiàn)美顏和濾鏡等等功能。

TPM

在經(jīng)過demo驗(yàn)證之后,我們將這個(gè)方案應(yīng)用到閑魚音視頻組件中,但改造過程中發(fā)現(xiàn)了一些問題。

上圖是攝像頭采集數(shù)據(jù)轉(zhuǎn)換為紋理的一段代碼,其中有兩個(gè)操作:首先是切進(jìn)程,將后面的OpenGL操作都切到cameraQueue中。然后是設(shè)置一次上下文。然后這種限制條件或者說是潛規(guī)則往往在開發(fā)過程中容易被忽略的。而這個(gè)條件一旦忽略后果就是出現(xiàn)一些莫名其妙的詭異問題極難排查。因此我們就希望能抽象出一套框架,由框架本身實(shí)現(xiàn)線程的切換、上下文和模塊生命周期等的管理,開發(fā)者接入框架以后只需要安心實(shí)現(xiàn)自己的算法,而不需要關(guān)心這些潛規(guī)則還有其他一些重復(fù)的邏輯操作。

在引入Flutter之前閑魚的音視頻架構(gòu)與大部分音視頻邏輯一樣采用分層架構(gòu):

1:底層是一些獨(dú)立模塊

2:SDK層是對(duì)底層模塊的封裝

3:最上層是UI層。

引入Flutter之后,通過分析各個(gè)模塊的使用場(chǎng)景,我們可以得出一個(gè)假設(shè)或者說是抽象:音視頻應(yīng)用在終端上可以歸納為視頻幀解碼之后視頻數(shù)據(jù)幀在各個(gè)模塊之間流動(dòng)的過程,基于這種假設(shè)去做Flutter音視頻框架的抽象。

咸魚Flutter多媒體開源組件

整個(gè)Flutter音視頻框架抽象分為管線和數(shù)據(jù)的抽象、模塊的抽象、線程統(tǒng)一管理和上下文同一管理四部分。

管線,其實(shí)就是視頻幀流動(dòng)的管道。數(shù)據(jù),音視頻中涉及到的數(shù)據(jù)包括紋理、Bit Map以及時(shí)間戳等。結(jié)合現(xiàn)有的應(yīng)用場(chǎng)景我們定義了管線流通數(shù)據(jù)以Texture為主數(shù)據(jù),同時(shí)可以選擇性的添加Bit Map等作為輔助數(shù)據(jù)。這樣的數(shù)據(jù)定義方式,避免重復(fù)的創(chuàng)建和銷毀紋理帶來的性能開銷以及多線程訪問紋理帶來的一些問題。也滿足一些特殊模塊對(duì)特殊數(shù)據(jù)的需求。同時(shí)也設(shè)計(jì)了紋理池來管理管線中的紋理數(shù)據(jù)。

模塊:如果把管線和數(shù)據(jù)比喻成血管和血液,那框架音視頻的場(chǎng)景就可以比喻成器官,我們根據(jù)模塊所在管線的位置抽象出采集、處理和輸出三個(gè)基類。這三個(gè)基類里實(shí)現(xiàn)了剛才說的線程切換,上下文切換,格式轉(zhuǎn)換等等共同邏輯,各個(gè)功能模塊通過集成自這些基類,可以避免很多重復(fù)勞動(dòng)。

線程:每一個(gè)模塊初始化的時(shí)候,初始化函數(shù)就會(huì)去線程管理的模塊去獲取自己的線程,線程管理模塊可以決定給初始化函數(shù)分配新的線程或者已經(jīng)分配過其他模塊的線程。

這樣有三個(gè)好處:

一是可以根據(jù)需要去決定一個(gè)線程可以掛載多少模塊,做到線程間的負(fù)載均衡。第二,多線程并發(fā)式能夠保證模塊內(nèi)的OpenGL操作是在當(dāng)前線程內(nèi)而不會(huì)跑到主線程去,徹底避免Flutter的OpenGL 環(huán)境被破壞。第三,多線程并行可以充分利用CPU多核架構(gòu),提升處理速度。

從Flutter端修改Flutter引擎將Context取出后,根據(jù)Context創(chuàng)建上下文的統(tǒng)一管理模塊,每一個(gè)模塊在初始化的時(shí)候會(huì)獲取它的線程,獲取之后會(huì)調(diào)用上下文管理模塊獲取自己的上下文。這樣可以保證每一個(gè)模塊的上下文都是與Flutter的上下文進(jìn)行Share的,每個(gè)模塊之間資源都是共享可見的,F(xiàn)lutter和音視頻native之間也是互相共享可見的。

基于上述框架如果要實(shí)現(xiàn)一個(gè)簡單的場(chǎng)景,比如畫面實(shí)時(shí)預(yù)覽和濾鏡處理功能,

1:需要選擇功能模塊,功能模塊包括攝像頭模塊、濾鏡處理模塊和Flutter畫面渲染模塊,

2:需要配置模塊參數(shù),比如采集分辨率、濾鏡參數(shù)和前后攝像頭設(shè)置等,

3:在創(chuàng)建視頻管線后使用已配置的參數(shù)創(chuàng)建模塊

4:最后管線搭載模塊,開啟管線就可以實(shí)現(xiàn)這樣簡單的功能。

上圖為整個(gè)功能實(shí)現(xiàn)的代碼和結(jié)構(gòu)圖。

結(jié)合上述音視頻框架,閑魚實(shí)現(xiàn)了Flutter多媒體開源組件。

組要包含四個(gè)基本組件分別是:

1:視頻圖像拍攝組件

2:播放器組件

3:視頻圖像編輯組件

4:相冊(cè)選擇組件

現(xiàn)在這些組件正在走內(nèi)部開源流程。預(yù)計(jì)9月份,相冊(cè)和播放器會(huì)實(shí)現(xiàn)開源。

后續(xù)展望和規(guī)劃

1:實(shí)現(xiàn)開頭所說的從底層SDK到UI的全鏈路的跨端開發(fā)。目前底層框架層和模塊層都是各個(gè)平臺(tái)各自實(shí)現(xiàn),反而是Flutter的UI端進(jìn)行了跨平臺(tái)的統(tǒng)一,所以后續(xù)會(huì)將底層也按照音視頻常用做法把邏輯下沉到C++層,盡可能的實(shí)現(xiàn)全鏈路跨平臺(tái)。

2:第二部分內(nèi)容為開源共建,閑魚開源的內(nèi)容不僅包括拍攝、編輯組件,還包括了很多底層模塊,希望有開發(fā)者在基于Flutter開發(fā)音視頻應(yīng)用時(shí)可以充分利用閑魚開源出的音視頻模塊能力,搭建APP框架,開發(fā)者只要去負(fù)責(zé)實(shí)現(xiàn)特殊需求模塊就可以,盡可能的減少重復(fù)勞動(dòng)。


當(dāng)前標(biāo)題:flutter混合優(yōu)化,flutter 列表優(yōu)化
網(wǎng)址分享:http://weahome.cn/article/dsigjpg.html

其他資訊

在線咨詢

微信咨詢

電話咨詢

028-86922220(工作日)

18980820575(7×24)

提交需求

返回頂部