Android - 如何以编程方式截取屏幕截图

Ava*_*i Y 15 java android

当我的应用程序安装并在后台运行200毫秒时,我需要以编程方式截取Android设备或模拟器,并将图像保存在我的计算机中.我已使用下面的代码实现了此过程,仅在我的应用程序位于前台时才有效.当我的应用程序也在后台时,我想截取屏幕截图.以下是我的代码:

public static Bitmap takeScreenshot(Activity activity, int ResourceID) { 
    Random r = new Random();
    int iterator=r.nextInt();   
     String mPath = Environment.getExternalStorageDirectory().toString() + "/screenshots/";
    View v1 = activity.getWindow().getDecorView().findViewById(ResourceID);
    v1.measure(MeasureSpec.makeMeasureSpec(0, MeasureSpec.UNSPECIFIED), 
            MeasureSpec.makeMeasureSpec(0, MeasureSpec.UNSPECIFIED));
    v1.layout(0, 0, v1.getMeasuredWidth(), v1.getMeasuredHeight()); 
    v1.setDrawingCacheEnabled(true);
    final Bitmap bitmap = Bitmap.createBitmap(v1.getDrawingCache());
    Bitmap resultBitmap = Bitmap.createScaledBitmap(bitmap, 640, 480, false);
    v1.setDrawingCacheEnabled(false);
    File imageFile = new File(mPath);
    imageFile.mkdirs();
    imageFile = new File(imageFile+"/"+iterator+"_screenshot.png");
    try {
        ByteArrayOutputStream bos = new ByteArrayOutputStream();
        resultBitmap.compress(CompressFormat.PNG, 100, bos);
        byte[] bitmapdata = bos.toByteArray();

        //write the bytes in file
        FileOutputStream fos = new FileOutputStream(imageFile);
        fos.write(bitmapdata);
        fos.flush();
        fos.close();    
    } catch (FileNotFoundException e) {
        e.printStackTrace();
    } catch (IOException e) {
        e.printStackTrace();
    }
    return bitmap;
    }  
Run Code Online (Sandbox Code Playgroud)

如何以Devices -> DDMS编程方式实现Screencapture的"刷新"和"保存"按钮的功能?我能做到吗?

Vis*_*nan 17

如果您的手机已植根,请尝试此操作

Process sh = Runtime.getRuntime().exec("su", null,null);

                    OutputStream  os = sh.getOutputStream();
                    os.write(("/system/bin/screencap -p " + "/sdcard/img.png").getBytes("ASCII"));
                    os.flush();

                    os.close();
                    sh.waitFor();
Run Code Online (Sandbox Code Playgroud)

然后将img.png作为位图读取并将其转换为jpg,如下所示

Bitmap screen = BitmapFactory.decodeFile(Environment.getExternalStorageDirectory()+         
File.separator +"img.png");

//my code for saving
    ByteArrayOutputStream bytes = new ByteArrayOutputStream();
    screen.compress(Bitmap.CompressFormat.JPEG, 15, bytes);

//you can create a new file name "test.jpg" in sdcard folder.

File f = new File(Environment.getExternalStorageDirectory()+ File.separator + "test.jpg");
            f.createNewFile();
//write the bytes in file
    FileOutputStream fo = new FileOutputStream(f);
    fo.write(bytes.toByteArray());
// remember close de FileOutput

    fo.close();
Run Code Online (Sandbox Code Playgroud)

如果您的应用程序在后台,除非您扎根,否则您无权访问该屏幕,即使您在后台,上面的代码也可以最有效地截取屏幕截图.

UPDATE

谷歌有一个库,你可以在没有生根的情况下截取屏幕截图,我试过了,但我确信它会尽快消耗内存.

试试http://code.google.com/p/android-screenshot-library/


swi*_*Boy 13

这是实现它的方法.

Android通过代码拍摄屏幕截图

结果输出:

在此输入图像描述

在此输入图像描述

public class CaptureScreenShots extends Activity {
    LinearLayout L1;
    ImageView image;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.screen_shots);
         L1 = (LinearLayout) findViewById(R.id.LinearLayout01);
            Button but = (Button) findViewById(R.id.munchscreen);
            but.setOnClickListener(new OnClickListener() {

                @Override
                public void onClick(View v) {
                    View v1 = L1.getRootView();
                    v1.setDrawingCacheEnabled(true);
                    Bitmap bm = v1.getDrawingCache();
                    BitmapDrawable bitmapDrawable = new BitmapDrawable(bm);
                    image = (ImageView) findViewById(R.id.screenshots);
                    image.setBackgroundDrawable(bitmapDrawable);
                }
            });
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        getMenuInflater().inflate(R.menu.screen_shots, menu);
        return true;
    }

}
Run Code Online (Sandbox Code Playgroud)

  • 如果应用程序在前台,这不会起作用吗? (2认同)
  • 不推荐使用`new BitmapDrawable(bitmap)`构造函数.而是使用`image.setImageBitmap(bm)` (2认同)
  • 如果视图层次结构中存在SurfaceView,则此方法无效,因为SurfaceView没有绘图缓存.您将在屏幕截图中看到黑色矩形. (2认同)