Android多媒体二:Android 5.0新增的屏幕捕捉
Android 5.0新增了MediaProjectionManager管理器,该管理器可以非常方便地实现屏幕捕捉功能。
使用MediaProjectionManager实现屏幕捕捉的步骤如下。
- 以MEDIA_PROJECTION_SERVICE为参数,调用Context.getSystemService()方法即可获取MediaProjectionManager实例。
- 调用MediaProjectionManager对象的createScreenCaptureIntent()方法创建一个屏幕捕捉的Intent。
- 调用startActivityForResult()方法启动第2步得到的Intent,这样即可启动屏幕捕捉的Intent。
- 重写onActivityResult()方法,在该方法中通过MediaProjectionManager对象来获取MediaProjection对象,在该对象中即可获取被捕获的屏幕。
实例:捕获当前屏幕
com/example/administrator/MainActivity.java
package com.example.administrator;
import android.annotation.TargetApi;
import android.app.Activity;
import android.content.Context;
import android.content.Intent;
import android.hardware.display.DisplayManager;
import android.hardware.display.VirtualDisplay;
import android.media.projection.MediaProjection;
import android.media.projection.MediaProjectionManager;
import android.os.Build;
import android.os.Bundle;
import android.support.annotation.RequiresApi;
import android.util.DisplayMetrics;
import android.view.Surface;
import android.view.SurfaceView;
import android.view.View;
import android.view.ViewGroup;
import android.widget.Toast;
import android.widget.ToggleButton;
public class MainActivity extends Activity implements View.OnClickListener {
private static final int CAPTURE_CODE = 0x123;
private MediaProjectionManager projectionManager;
private int screenDensity;
private int displayWidth = 360;
private int displayHeight = 640;
private boolean screenSharing;
private MediaProjection mediaProjection;
private VirtualDisplay virtualDisplay;
private Surface surface;
private SurfaceView surfaceView;
private ToggleButton tb;
@TargetApi(Build.VERSION_CODES.LOLLIPOP)
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
// 获取屏幕分辨率
DisplayMetrics metrics = new DisplayMetrics();
getWindowManager().getDefaultDisplay().getMetrics(metrics);
screenDensity = metrics.densityDpi;
// 获取应用界面上的SurfaceView组件
surfaceView = (SurfaceView) findViewById(R.id.surface);
tb = findViewById(R.id.tb);
tb.setOnClickListener(this);
surface = surfaceView.getHolder().getSurface();
// 控制界面上的SurfaceView组件的宽度和高度
ViewGroup.LayoutParams lp = surfaceView.getLayoutParams();
lp.height = displayHeight;
lp.width = displayWidth;
surfaceView.setLayoutParams(lp);
// 获取MediaProjectionManager管理器
projectionManager = (MediaProjectionManager) getSystemService(Context.MEDIA_PROJECTION_SERVICE); // ①
}
// 当用户单击开关按钮时激发该方法
@TargetApi(Build.VERSION_CODES.LOLLIPOP)
@Override
public void onClick(View view) {
if (((ToggleButton) view).isChecked()) {
shareScreen();
} else {
stopScreenSharing();
}
}
@TargetApi(Build.VERSION_CODES.LOLLIPOP)
@Override
public void onDestroy() {
super.onDestroy();
if (mediaProjection != null) {
mediaProjection.stop();
mediaProjection = null;
}
}
@RequiresApi(api = Build.VERSION_CODES.LOLLIPOP)
private void shareScreen() {
screenSharing = true;
if (surface == null) {
return;
}
if (mediaProjection == null) {
Intent intent = projectionManager.createScreenCaptureIntent(); // ②
startActivityForResult(intent, CAPTURE_CODE); // ③
return;
}
}
@TargetApi(Build.VERSION_CODES.KITKAT)
private void stopScreenSharing() {
screenSharing = false;
if (virtualDisplay == null) {
return;
}
virtualDisplay.release();
}
@TargetApi(Build.VERSION_CODES.LOLLIPOP)
@Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
if (requestCode == CAPTURE_CODE) {
// 如果resultCode不等于RESULT_OK,表明用户拒绝了屏幕捕捉
if (resultCode != RESULT_OK) {
Toast.makeText(this, "用户取消了屏幕捕捉", Toast.LENGTH_SHORT).show();
return;
}
mediaProjection = projectionManager.getMediaProjection(resultCode, data); // ④
virtualDisplay = mediaProjection.createVirtualDisplay("屏幕捕捉", displayWidth, displayHeight, screenDensity, DisplayManager.VIRTUAL_DISPLAY_FLAG_AUTO_MIRROR, surface, null /*Callbacks*/, null /*Handler*/);
}
}
}