背景:
游戲機中想加入舞蹈元素,最先的想法是開發舞蹈游戲,然后通過動畫來表現舞蹈,給用戶提供舞蹈教學方面的體驗,但是舞蹈游戲本身的開發就需要很長的時間(就人太少),不用談后續的舞蹈和音樂的版權啦,所以現在想走另外一條途徑,在unity中播放舞蹈教學視頻,加上UI和一些檢測來實現舞蹈教學,而且這套框架寫完之后,內容很容易擴展,畢竟不需要針對每個舞蹈設計動畫。但是Unity中視頻播放就是各種蛋疼,尤其是在android下面,OK ,下面的內容很多是從網上整理下來:
1 Win/Mac
首先在Windows和Mac上 需要Quick Time7.0以上的版本。Unity支持的視頻播放格式還是蠻多如.mov、.mpg、.mpeg、.mp4、.avi、.asf,甚至.H264等等,使用起來也很簡單,真的很簡~~單。
在WIN/MAC下,Unity提供了MovieTexture紋理,對導入的視頻Unity會自動進行轉換。MovieTexture繼承與Texture類,提供了視頻播放中需要的簡單控制播放/暫停/停止:
Pause | Pauses playing the movie. |
Play | Starts playing the movie. |
Stop | Stops playing the movie, and rewinds it to the beginning. |
MovieTexture給出的參數也是在不多,考慮到視頻會是從網絡中進行下載,檢測isReadyToPlay很有必要,isPlaying給出是否在播放的參數,loop控制是否循環播放,duration是一個很有用的東西,給出當前播放到的位置。
audioClip | Returns the AudioClip belonging to the MovieTexture. |
duration | The time, in seconds, that the movie takes to play back completely. |
isPlaying | Returns whether the movie is playing or not. |
isReadyToPlay | If the movie is downloading from a web site, this returns if enough data has been downloaded so playback should be able to start without interruptions. |
loop | Set this to true to make the movie loop. |
測試一下,具體的使用方式雨松給出的很詳細:Unity3D研究之兩種方式播放游戲視頻。以在平面顯示為例,測試代碼的核心代碼如下:
1 renderer.material.mainTexture = movie; //設置材質
2
3 movie.loop = true; //循環播放
4 movie.Play(); //播放
5 movie.Pause(); //暫停
6 movie.Stop();
unity中提供的視頻播放功能還是先對簡單化,如果只是簡單的播放倒也無所謂,但是如果是進行視頻方面的開發,肯定不能滿足要求。例如常用的 回放、快進、快退、定點播放等等都沒提供。對於快進,有網友通過在同一個GameObject上綁定一個AudioSource,利用其pitch參數可以進行控制,不過我沒有測出來。
還有一種方法就是合適的第三方插件,如AVPro QuickTime,可以實現快進、快退、頂點播放、多窗口播放等等(如果在window下,例子中是視頻文件以及內部的參數中.bin的后綴要去掉),不過這個插件只能在win/mac上使用~~ 。
這個插件的代碼是研究unity底層不錯的例子,Unity實現的功能有限,但是可以通過利用視頻編解碼庫對視頻進行解碼,然后利用Unity底層提供的渲染功能(如GL)實現表面的視頻播放功能。
![[IMG]](/image/aHR0cDovL3d3dy5yZW5kZXJoZWFkcy5jb20vcG9ydGZvbGlvL1VuaXR5QVZQcm9RdWlja1RpbWUvaW1hZ2VzL2RlbW8uanBn.png)
![[IMG]](/image/aHR0cDovL3d3dy5yZW5kZXJoZWFkcy5jb20vcG9ydGZvbGlvL1VuaXR5QVZQcm9RdWlja1RpbWUvaW1hZ2VzL2NvbXBvbmVudHMucG5n.png)
2 移動端
在移動端,unity並不提供MovieTexture,AVPro QuickTime也用不了,其最基本的顯示方案使用通過PlayFullScreenMovie()函數進行全屏播放,根據其官網解釋,主要有以下方面:
(1)視頻流直接從設備存儲器中獲得,所以文件只能是單獨提供,視頻文件放置在StreamingAssets 文件夾中
(2) 視頻播放過陳中,Unity將會停止;播放結束后unity自動恢復;播放過程中屏幕中的顏色會變為播放器的背景顏色,播放之后恢復。
(3)在IOS中,內部實際上是調用MPMoviePlayerController的方法
(4)能夠支持的格式: .mov, .mp4, .mpv, and .3gp ,H.264,MPEG-4 Part 2 video
Handheld.PlayFullScreenMovie ("StarWars.mp4", Color.black, FullScreenMovieControlMode.CancelOnInput);
話不投機,兩句多,還是果斷第三方插件,Mobile movie texture for android 就是很不錯的東西,利用開源視頻編解碼庫Theora進行視頻解碼,然后通過Unity Texture實現顯示。下圖為多視頻顯示效果:
應用中的一些問題:
(1)因為視頻編解碼庫是使用Theora ,所以只能支持OGG、OGV格式的視頻和音頻,如果要使用其他格式則需要轉換一下,可以Theora Converter .NET工具進行轉換。
(2)視頻seek功能不是很精確,雖然能用
(3)多視頻播放問題,如果想要多少視頻同時播放,需要理解內部代碼的實現,修改后可以湊合着使用。多視頻播放的另外一個問題是效率問題,如果是N個視頻,可能就會有N個后台線程在進行解碼操作,相應的也會有N個渲染管道進行渲染,我在RK3188上進行三個不同視頻的播放,就會有卡頓。多視頻播放中間理解的關鍵代碼在下面,Texture2D.CreateExternalTexture 函數從視頻中獲得貼圖資源,SetTextures()進行繪制,如果使用多個視頻,需要多個材質(也就是多個渲染管道)。
private void AllocateTexures() { m_ChannelTextures[0] = Texture2D.CreateExternalTexture(m_yStride, m_yHeight, TextureFormat.BGRA32, false, false, GetNativeYHandle(m_nativeContext)); m_ChannelTextures[1] = Texture2D.CreateExternalTexture(m_uvStride, m_uvHeight, TextureFormat.RGBA32, false, false, GetNativeCrHandle(m_nativeContext)); m_ChannelTextures[2] = Texture2D.CreateExternalTexture(m_uvStride, m_uvHeight, TextureFormat.RGBA32, false, false, GetNativeCbHandle(m_nativeContext)); if (m_movieMaterials != null) { for (int i = 0; i < m_movieMaterials.Length; ++i) { var mat = m_movieMaterials[i]; if (mat != null) { SetTextures(mat); } } } } public void SetTextures(Material material) { material.SetTexture("_YTex", m_ChannelTextures[0]); material.SetTexture("_CrTex", m_ChannelTextures[1]); material.SetTexture("_CbTex", m_ChannelTextures[2]); material.SetTextureScale("_YTex", m_uvYScale); material.SetTextureOffset("_YTex", m_uvYOffset); material.SetTextureScale("_CbTex", m_uvCrCbScale); material.SetTextureOffset("_CbTex", m_uvCrCbOffset); }
轉載 請注明:細雨淅淅