1.SurfaceView 就是自帶Surface 的 view,他是一個View的子類別,所以和其他 View一樣,可以在螢幕上展是東西接收用戶輸入資訊,具有 View 的生命周期call back function,如 onMeasure、onLayout、onDraw、onTouchEvent 等
2.SurfaceView在子線程(叫做渲染線程)中對Surface進行繪製,將繪製好的畫面呈現給View,不會影響主線程與用戶的交互操作
3.SurfaceView採用雙緩衝技術,繪製效率高
SurfaceView是在一個新起的单独线程中可以重新繪製畫面,而View必须在UI的主线程中更新画面。如果长时间在UI線程進行化畫面更新,可能会阻塞UI線程,導致UI的按键,触摸等不能得到及时响应,而如果在子线程中进行不断的画面更新操作则不会影响主线程。所以当涉及到UI的快速刷新时就需要用到SurfaceView(如游戏,视频等)
引用 : https://www.jianshu.com/p/f7c3299c3576
SurfaceHolder
SurfaceHolder是一个接口,是对 SurfaceView 的 Surface 的包装,不但在 SurfaceHolder.callback 接口中负责 Surface 创建和销毁的回调,而且还对 Surface 的关键方法 LockCanvas()、unLockCanvasAndPost() 方法进行了线程安全的包装,所以 SurfaceHolder 是 Surface 对象的持有者,负责 Surface 的生命周期中的对 Surface 操作的方法的调用
SurfaceView创建
新建一个类继承自SurfaceView并实现SurfaceHolder.Callback接口,然后重写以下方法:
(1)在surface创建时触发
public void surfaceCreated(SurfaceHolder holder) { }
(2)在surface大小发生改变时触发
public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) { }
(3)在surface销毁时触发
public void surfaceDestroyed(SurfaceHolder holder) { }
Surfaceview使用過程:繼承SurfaceView並實現SurfaceHolder.Callback的interface ----> SurfaceView.getHolder()獲得SurfaceHolder對象 ---->SurfaceHolder.addCallback(callback)添加回调函数---->SurfaceHolder.lockCanvas()獲得Canvas對像並鎖定畫布----> Canvas绘画 ---->SurfaceHolder.unlockCanvasAndPost(Canvas canvas)结束鎖定畫圖,並提交改變,將圖型顯示。
以上SurfaceView介紹後接著介紹SurfaceView新增的流程順序
1.find SurfaceView id
2.getHolder()
3.Holder add Callback
Layout xml
android:id="@+id/outside_view" android:layout_width="2560px" android:layout_height="600px" app:layout_constraintLeft_toLeftOf="@id/cluster_layout_background" app:layout_constraintTop_toTopOf="@id/cluster_layout_background" android:layout_marginTop="0px" android:layout_marginLeft="0px" />
import階段
import android.media.MediaPlayer;
程式宣告階段
public class MainActivity extends AppCompatActivity implements
MediaPlayer.OnPreparedListener, MediaPlayer.OnCompletionListener,
MediaPlayer.OnErrorListener, SurfaceHolder.Callback {
變數宣告階段
private String mFilePath = "";private MediaPlayer mOutviewPlayer;private SurfaceView mSurfaceView_outside;private SurfaceHolder mSurfaceHolder_outside;
function宣告階段
@Overridepublic void surfaceCreated(SurfaceHolder holder) { if(DBG) Log.d(LOG_TAG, "surfaceCreated"); mOutviewPlayer = new MediaPlayer(); mOutviewPlayer.setDisplay(mSurfaceHolder_outside); try { String file_common_dir = Environment.getExternalStorageDirectory() + "/Download/"; mFilePath = file_common_dir + "outview.mp4"; mOutviewPlayer.setDataSource(mFilePath); mOutviewPlayer.setLooping(true); mOutviewPlayer.prepare(); mOutviewPlayer.start(); if(DBG) Log.d(LOG_TAG, "[KH]Video is playing."); } catch (Exception e) { e.printStackTrace(); } } @Overridepublic void surfaceChanged(SurfaceHolder holder, int format, int width, int height) { Log.e("video","surfaceChanged");} @Overridepublic void surfaceDestroyed(SurfaceHolder holder) { Log.e("video","surfaceDestroyed"); super.onDestroy();}
onCreate宣告階段
mSurfaceView_outside = (SurfaceView)findViewById(R.id.outside_view);mSurfaceHolder_outside = mSurfaceView_outside.getHolder(); // mSurfaceHolder_outside是mSurfaceView_outside的控制接口mSurfaceHolder_outside.addCallback(this);
onDestory宣告階段
@Overrideprotected void onDestroy() { super.onDestroy(); if (mOutviewPlayer.isPlaying()) { mOutviewPlayer.stop(); } mOutviewPlayer.release();}
打完收工
沒有留言:
張貼留言