首页 诗词 字典 板报 句子 名言 友答 励志 学校 网站地图
当前位置: 首页 > 教程频道 > 移动开发 > Android >

Android 4.0 截屏(Screenshot)代码流程总结

2013-01-09 
Android 4.0 截屏(Screenshot)代码流程小结原文地址:http://blog.csdn.net/hk_256/article/details/730659

Android 4.0 截屏(Screenshot)代码流程小结

原文地址:http://blog.csdn.net/hk_256/article/details/7306590?,转载请注明出处

?

一、基本介绍

?

???????? 在Android 4.0 之前,Android手机上如果要使用截屏功能,只能通过Root手机,且使用第3方截图软件来实现截屏功能。

???????? Android4.0中,系统自带了截屏功能,使用方法是音量下(VOLUME_DOWN)键+电源(Power)键。

?

???????? 在同时按下2键并保持0.5s左右后,会听到咔嚓一声响声,并弹出如下的一个浮动动画,显示截图效果。

Android 4.0 截屏(Screenshot)代码流程总结

?

?

二、代码调用流程

?

???????? 以模块来划分的话,截图功能的代码会依次调用Policy,SystemUI,Surface相关的代码,具体流程如下流程图所示

?

Android 4.0 截屏(Screenshot)代码流程总结

?

?

? ? ? ???Policy(PhoneWindowManager.java):在此处完成Key的捕获,当VOLUME_DOWN和Power键被几乎同时按下后,向SystemUI发送Message开始截图。

?

???????? SystemUI(TakeScreenshotService.java和GlobalScreenshot.java):收到来自Client端的截屏请求后,开始调用Surface的API截屏,并将截取到的图片通过WindowManager以浮动窗口的形式显示给用户查看。

?

???????? Surface(Surface.java和android_view_Surface.cpp):Framework层的Surface.java只是提供一个native方法,实际实现在JNI处的android_view_Surface.cpp中的doScreenshot(...)方法。

?

?

三、App端如何使用截屏功能

?

???????? 以目前代码情况看,Surface.java中的screenshot方法是有@hide标记的,即在默认的SDK中是没有此方法的,暂不支持App端直接使用。

?

???????? 因为只是@hide标记,如果App要使用,当然也是有方法的,但会和手机ROM有依赖性。我所使用的方法是,在Android源码环境下进行编译,为app赋予system的share uid和platform的签名,然后就可以在4.0的手机中使用App来截屏了。

?

???????? 关键步骤:

1) 在AndroidManifest.xml中加入android:sharedUserId="android.uid.system"?属性

2)在Android.mk中加入platform签名属性,并在源码环境下编译。或者将相关jar包引入到Eclipse中做第3方库引用,并将生成的apk重新打上platform签名

?

?

注:

???????? 在SurfceFlinger.cpp的onTransact方法中,有对截屏的操作进行权限认证,所以需要为app使用system的shareUserId。

???????? 另:从此处代码看,使用android.permission.READ_FRAME_BUFFER的permission应该也可以使用,但测试时通过这种方式未实现,可能哪里操作不对,也有可能Google还只是预留给后续改进而已。

Android 4.0 截屏(Screenshot)代码流程总结

Android 4.0 截屏(Screenshot)代码流程总结

?

博客地址:http://blog.csdn.net/hk_256?,转载请注明出处

?

附录:App的源代码文件:

1. Activity文件

[java]?view plaincopyprint?
  1. package?com.arvinhe.testscreenshot;??
  2. ??
  3. import?android.app.Activity;??
  4. import?android.content.Context;??
  5. import?android.graphics.Bitmap;??
  6. import?android.graphics.Canvas;??
  7. import?android.graphics.Matrix;??
  8. import?android.os.Bundle;??
  9. import?android.util.DisplayMetrics;??
  10. import?android.view.Display;??
  11. import?android.view.Surface;??
  12. import?android.view.View;??
  13. import?android.view.WindowManager;??
  14. import?android.view.View.OnClickListener;??
  15. import?android.widget.Button;??
  16. import?android.widget.ImageView;??
  17. ??
  18. public?class?TestScreenShotActivity?extends?Activity?implements?OnClickListener{??
  19. ??????
  20. ????private?ImageView?img_display;??
  21. ????private?Button?bt_screenshot;??
  22. ??????
  23. ????private?Display?mDisplay;??
  24. ????private?DisplayMetrics?mDisplayMetrics;??
  25. ????private?Matrix?mDisplayMatrix;??
  26. ????private?Bitmap?mScreenBitmap;??
  27. ????private?WindowManager?mWindowManager;??
  28. ??????
  29. ????@Override??
  30. ????public?void?onCreate(Bundle?savedInstanceState)?{??
  31. ????????super.onCreate(savedInstanceState);??
  32. ????????setContentView(R.layout.main);??
  33. ??????????
  34. ????????bt_screenshot?=?(Button)findViewById(R.id.bt_screenshot);??
  35. ????????img_display?=?(ImageView)findViewById(R.id.img_display);??
  36. ??????????
  37. ????????bt_screenshot.setOnClickListener(this);??
  38. ??????????
  39. ????????mDisplayMatrix?=?new?Matrix();??
  40. ??????????
  41. ????????mWindowManager?=?(WindowManager)?this.getSystemService(Context.WINDOW_SERVICE);??
  42. ????????mDisplay?=?mWindowManager.getDefaultDisplay();??
  43. ????????mDisplayMetrics?=?new?DisplayMetrics();??
  44. ????????mDisplay.getRealMetrics(mDisplayMetrics);??
  45. ????}??
  46. ??
  47. ????@Override??
  48. ????public?void?onClick(View?v)?{??
  49. ????????if(v.equals(bt_screenshot)){??
  50. ????????????mDisplay.getRealMetrics(mDisplayMetrics);??
  51. ????????????float[]?dims?=?{mDisplayMetrics.widthPixels,?mDisplayMetrics.heightPixels};??
  52. ????????????float?degrees?=?getDegreesForRotation(mDisplay.getRotation());??
  53. ????????????boolean?requiresRotation?=?(degrees?>?0);??
  54. ????????????if?(requiresRotation)?{??
  55. ????????????????//?Get?the?dimensions?of?the?device?in?its?native?orientation??
  56. ????????????????mDisplayMatrix.reset();??
  57. ????????????????mDisplayMatrix.preRotate(-degrees);??
  58. ????????????????mDisplayMatrix.mapPoints(dims);??
  59. ????????????????dims[0]?=?Math.abs(dims[0]);??
  60. ????????????????dims[1]?=?Math.abs(dims[1]);??
  61. ????????????}??
  62. ????????????mScreenBitmap?=?Surface.screenshot((int)?dims[0],?(int)?dims[1]);??
  63. ????????????if?(requiresRotation)?{??
  64. ????????????????//?Rotate?the?screenshot?to?the?current?orientation??
  65. ????????????????Bitmap?ss?=?Bitmap.createBitmap(mDisplayMetrics.widthPixels,??
  66. ????????????????????????mDisplayMetrics.heightPixels,?Bitmap.Config.ARGB_8888);??
  67. ????????????????Canvas?c?=?new?Canvas(ss);??
  68. ????????????????c.translate(ss.getWidth()?/?2,?ss.getHeight()?/?2);??
  69. ????????????????c.rotate(degrees);??
  70. ????????????????c.translate(-dims[0]?/?2,?-dims[1]?/?2);??
  71. ????????????????c.drawBitmap(mScreenBitmap,?0,?0,?null);??
  72. ????????????????c.setBitmap(null);??
  73. ????????????????mScreenBitmap?=?ss;??
  74. ????????????}??
  75. ??
  76. ????????????//?If?we?couldn't?take?the?screenshot,?notify?the?user??
  77. ????????????if?(mScreenBitmap?==?null)?{??
  78. ?????????????????
  79. ????????????????return;??
  80. ????????????}??
  81. ??
  82. ????????????//?Optimizations??
  83. ????????????mScreenBitmap.setHasAlpha(false);??
  84. ????????????mScreenBitmap.prepareToDraw();??
  85. ??????????????
  86. ????????????img_display.setImageBitmap(mScreenBitmap);??
  87. ????????}??
  88. ??????????
  89. ????}??
  90. ??????
  91. ????/**?
  92. ?????*?@return?the?current?display?rotation?in?degrees?
  93. ?????*/??
  94. ????private?float?getDegreesForRotation(int?value)?{??
  95. ????????switch?(value)?{??
  96. ????????case?Surface.ROTATION_90:??
  97. ????????????return?360f?-?90f;??
  98. ????????case?Surface.ROTATION_180:??
  99. ????????????return?360f?-?180f;??
  100. ????????case?Surface.ROTATION_270:??
  101. ????????????return?360f?-?270f;??
  102. ????????}??
  103. ????????return?0f;??
  104. ????}??
  105. }??

2. AndroidManifest.xml文件

[html]?view plaincopyprint?
  1. <?xml?version="1.0"?encoding="utf-8"?>??
  2. <manifest?xmlns:android="http://schemas.android.com/apk/res/android"??
  3. ????package="com.arvinhe.testscreenshot"??
  4. ????android:versionCode="1"??
  5. ????android:versionName="1.0"???
  6. ????android:sharedUserId="android.uid.system">??
  7. ??
  8. ????<uses-sdk?android:minSdkVersion="15"?/>??
  9. ??????
  10. ??
  11. ????<application??
  12. ????????android:icon="@drawable/ic_launcher"??
  13. ????????android:label="@string/app_name"?>??
  14. ????????<activity??
  15. ????????????android:name=".TestScreenShotActivity"??
  16. ????????????android:label="@string/app_name"?>??
  17. ????????????<intent-filter>??
  18. ????????????????<action?android:name="android.intent.action.MAIN"?/>??
  19. ??
  20. ????????????????<category?android:name="android.intent.category.LAUNCHER"?/>??
  21. ????????????</intent-filter>??
  22. ????????</activity>??
  23. ????</application>??
  24. ??
  25. </manifest>??

3. Layout文件

[html]?view plaincopyprint?
  1. <?xml?version="1.0"?encoding="utf-8"?>??
  2. <LinearLayout?xmlns:android="http://schemas.android.com/apk/res/android"??
  3. ????android:layout_width="fill_parent"??
  4. ????android:layout_height="fill_parent"??
  5. ????android:orientation="vertical"?>??
  6. ??
  7. ????<TextView??
  8. ????????android:layout_width="fill_parent"??
  9. ????????android:layout_height="wrap_content"??
  10. ????????android:text="@string/hello"?/>??
  11. ??????
  12. ????<Button??
  13. ????????android:id="@+id/bt_screenshot"??
  14. ????????android:layout_width="fill_parent"??
  15. ????????android:layout_height="wrap_content"??
  16. ????????android:text="Screen?Shot"??
  17. ????????/>??
  18. ??????
  19. ????<ImageView???
  20. ????????android:id="@+id/img_display"??
  21. ????????android:layout_width="fill_parent"??
  22. ????????android:layout_height="wrap_content"??
  23. ????????android:src="@drawable/ic_launcher"/>??
  24. ??
  25. </LinearLayout>??

附录:App运行效果截图

Android 4.0 截屏(Screenshot)代码流程总结?Android 4.0 截屏(Screenshot)代码流程总结

热点排行