android 截屏 简书,Android之截屏实现

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 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();

}

}

}

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值