Android5.0截屏是不需要root权限,因为google开放了它的api.
在Application子类中添加:
public class MyApplication extends Application {
Intent intent;
int resultCode;
private MediaProjectionManager mMediaProjectionManager;
public MediaProjectionManager getmMediaProjectionManager() {
return mMediaProjectionManager;
}
public void setmMediaProjectionManager(MediaProjectionManager mMediaProjectionManager) {
this.mMediaProjectionManager = mMediaProjectionManager;
}
public int getResultCode() {
return resultCode;
}
public void setResultCode(int resultCode) {
this.resultCode = resultCode;
}
public Intent getIntent() {
return intent;
}
public void setIntent(Intent intent) {
this.intent = intent;
}
}
MainActivity中代码如下:
public class MainActivity extends ActionBarActivity {
private int result = 0;
private Intent intent = null;
private int REQUEST_MEDIA_PROJECTION = 1;
private MediaProjectionManager mMediaProjectionManager;
@TargetApi(Build.VERSION_CODES.LOLLIPOP)
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mMediaProjectionManager = (MediaProjectionManager) getApplication().getSystemService(Context.MEDIA_PROJECTION_SERVICE);
startIntent();
}
@TargetApi(Build.VERSION_CODES.LOLLIPOP)
private void startIntent() {
if (intent != null && result != 0) {
((MyApplication) getApplication()).setResult(result);
((MyApplication) getApplication()).setIntent(intent);
Intent intent = new Intent(getApplicationContext(), Service1.class);
startService(intent);
} else {
startActivityForResult(mMediaProjectionManager.createScreenCaptureIntent(), REQUEST_MEDIA_PROJECTION);
((MyApplication) getApplication()).setMediaProjectionManager(mMediaProjectionManager);
}
}
@TargetApi(Build.VERSION_CODES.LOLLIPOP)
@Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
if (requestCode == REQUEST_MEDIA_PROJECTION) {
if (resultCode != Activity.RESULT_OK) {
return;
} else if (data != null && resultCode != 0) {
result = resultCode;
intent = data;
((MyApplication) getApplication()).setResult(resultCode);
((MyApplication) getApplication()).setIntent(data);
Intent intent = new Intent(getApplicationContext(), Service1.class);
startService(intent);
finish();
}
}
}
}
Service1中的相关代码:
import android.annotation.TargetApi;
import android.app.Service;
import android.content.Context;
import android.content.Intent;
import android.graphics.Bitmap;
import android.hardware.display.DisplayManager;
import android.hardware.display.VirtualDisplay;
import android.media.Image;
import android.media.ImageReader;
import android.media.projection.MediaProjection;
import android.media.projection.MediaProjectionManager;
import android.net.Uri;
import android.os.Build;
import android.os.Environment;
import android.os.IBinder;
import android.util.DisplayMetrics;
import android.view.View;
import android.view.WindowManager;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.nio.ByteBuffer;
import java.text.SimpleDateFormat;
public class Service1 extends Service{
private MediaProjection mMediaProjection = null;
private VirtualDisplay mVirtualDisplay = null;
public static int mResultCode = 0;
public static Intent mResultData = null;
public static MediaProjectionManager mMediaProjectionManager1 = null;
private WindowManager mWindowManager1 = null;
private int windowWidth = 0;
private int windowHeight = 0;
private ImageReader mImageReader = null;
private DisplayMetrics metrics = null;
private int mScreenDensity = 0;
public void onCreate() {
// TODO Auto-generated method stub
super.onCreate();
createFloatView();
createVirtualEnvironment();
}
@Override
public IBinder onBind(Intent intent) {
// TODO Auto-generated method stub
return null;
}
private void createFloatView() {
//在这里不介绍悬浮框,
mFloatView.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
// hide the button
mFloatView.setVisibility(View.INVISIBLE);
Handler handler1 = new Handler();
handler1.postDelayed(new Runnable() {
public void run() {
//start virtual
startVirtual();
}
}, 500);
Handler handler2 = new Handler();
handler2.postDelayed(new Runnable() {
public void run() {
//capture the screen
startCapture();
}
}, 1500);
Handler handler3 = new Handler();
handler3.postDelayed(new Runnable() {
public void run() {
mFloatView.setVisibility(View.VISIBLE);
//stopVirtual();
}
}, 1000);
}
});
}
private void createVirtualEnvironment() {
dateFormat = new SimpleDateFormat("yyyy_MM_dd_hh_mm_ss");
strDate = dateFormat.format(new java.util.Date());
pathImage = Environment.getExternalStorageDirectory().getPath() + "/Pictures/";
nameImage = pathImage + strDate + ".png";
mMediaProjectionManager1 = (MediaProjectionManager) getApplication().getSystemService(Context.MEDIA_PROJECTION_SERVICE);
mWindowManager1 = (WindowManager) getApplication().getSystemService(Context.WINDOW_SERVICE);
windowWidth = mWindowManager1.getDefaultDisplay().getWidth();
windowHeight = mWindowManager1.getDefaultDisplay().getHeight();
metrics = new DisplayMetrics();
mWindowManager1.getDefaultDisplay().getMetrics(metrics);
mScreenDensity = metrics.densityDpi;
mImageReader = ImageReader.newInstance(windowWidth, windowHeight, 0x1, 2); //ImageFormat.RGB_565
}
@TargetApi(Build.VERSION_CODES.LOLLIPOP)
public void startVirtual() {
if (mMediaProjection != null) {
virtualDisplay();
} else {
setUpMediaProjection();
virtualDisplay();
}
}
@TargetApi(Build.VERSION_CODES.LOLLIPOP)
public void setUpMediaProjection() {
mResultData = ((MyApplication) getApplication()).getIntent();
mResultCode = ((MyApplication) getApplication()).getResult();
mMediaProjectionManager1 = ((MyApplication) getApplication()).getMediaProjectionManager();
mMediaProjection = mMediaProjectionManager1.getMediaProjection(mResultCode, mResultData);
}
@TargetApi(Build.VERSION_CODES.LOLLIPOP)
private void virtualDisplay() {
mVirtualDisplay = mMediaProjection.createVirtualDisplay("screen-mirror",
windowWidth, windowHeight, mScreenDensity, DisplayManager.VIRTUAL_DISPLAY_FLAG_AUTO_MIRROR,
mImageReader.getSurface(), null, null);
}
@TargetApi(Build.VERSION_CODES.LOLLIPOP)
private void startCapture() {
strDate = dateFormat.format(new java.util.Date());
nameImage = pathImage + strDate + ".png";
Image image = mImageReader.acquireLatestImage();
int width = image.getWidth();
int height = image.getHeight();
final Image.Plane[] planes = image.getPlanes();
final ByteBuffer buffer = planes[0].getBuffer();
int pixelStride = planes[0].getPixelStride();
int rowStride = planes[0].getRowStride();
int rowPadding = rowStride - pixelStride * width;
Bitmap bitmap = Bitmap.createBitmap(width + rowPadding / pixelStride, height, Bitmap.Config.ARGB_8888);
bitmap.copyPixelsFromBuffer(buffer);
bitmap = Bitmap.createBitmap(bitmap, 0, 0, width, height);
image.close();
if (bitmap != null) {
try {
File fileImage = new File(nameImage);
if (!fileImage.exists()) {
fileImage.createNewFile();
}
FileOutputStream out = new FileOutputStream(fileImage);
if (out != null) {
bitmap.compress(Bitmap.CompressFormat.PNG, 100, out);
out.flush();
out.close();
Intent media = new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE);
Uri contentUri = Uri.fromFile(fileImage);
media.setData(contentUri);
this.sendBroadcast(media);
}
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
}
@TargetApi(Build.VERSION_CODES.LOLLIPOP)
private void tearDownMediaProjection() {
if (mMediaProjection != null) {
mMediaProjection.stop();
mMediaProjection = null;
}
}
private void stopVirtual() {
if (mVirtualDisplay == null) {
return;
}
mVirtualDisplay.release();
mVirtualDisplay = null;
}
@Override
public void onDestroy() {
// to remove mFloatLayout from windowManager
super.onDestroy();
// if (mFloatLayout != null) {
// mWindowManager.removeView(mFloatLayout);
// }
tearDownMediaProjection();
}
}
}
现在来介绍4.4截屏,不过需要root权限。可以在原生的Android系统中使用系统签名使用,模拟器就是用的Android原生系统,genymotion就可以。
废话不多说,上代码。
会使用adb 的同学可以试试。如下就在手机SD卡目录下生成名为shotscreene.png图片对象。
adb shell
shell@HWTIT-L6735:/ $ su -c "screencap -p /sdcard/shotscreen.png"
截屏代码,且保存为bitmap对象:
/**
* 截图
*/
public void doCaptureScreeKITKAT() {
List<String> command = new ArrayList<>();
command.add("/system/bin/screencap -p ");
getScreenShotStream(command.toArray(new String[]{}), true,
true);
}
/**
* 获取截屏流,转换成位图
*
* @param commands
* @param isRoot
* @param isNeedResultMsg
*/
public void getScreenShotStream(String[] commands, boolean isRoot, boolean isNeedResultMsg) {
if (commands == null || commands.length == 0)
return;
Process process = null;
DataOutputStream os;
try {
process = Runtime.getRuntime().exec(isRoot ? "su" : "sh");
os = new DataOutputStream(process.getOutputStream());
for (String command : commands) {
if (command == null) {
continue;
}
os.write(command.getBytes());
os.writeBytes("\\\\n");
os.flush();
}
os.writeBytes("exit\\\\n");
os.flush();
if (isNeedResultMsg) {
this.bitmap = BitmapFactory.decodeStream(process.getInputStream());
}
os.close();
} catch (IOException e) {
e.printStackTrace();
} catch (Exception e) {
e.printStackTrace();
} finally {
try {
if (process != null) {
process.exitValue();
}
} catch (IllegalThreadStateException e) {
process.destroy();
}
}
}