当前位置:   article > 正文

Android Camera拍照_android com.liql.photograph

android com.liql.photograph

Android 相机拍照的注意事项和基本使用请点击——Android Camera开发之基础知识篇

本文主要介绍Camera在项目中的代码实现:(经测试可用)

    

  1. package com.wj.shoes.shortvideo.view.fragment.photo;
  2. import android.annotation.TargetApi;
  3. import android.content.Context;
  4. import android.content.Intent;
  5. import android.content.pm.PackageManager;
  6. import android.graphics.Bitmap;
  7. import android.graphics.BitmapFactory;
  8. import android.graphics.BitmapRegionDecoder;
  9. import android.graphics.Matrix;
  10. import android.graphics.PixelFormat;
  11. import android.graphics.Rect;
  12. import android.hardware.Camera;
  13. import android.os.AsyncTask;
  14. import android.os.Build;
  15. import android.os.Bundle;
  16. import android.os.Handler;
  17. import android.support.annotation.Nullable;
  18. import android.support.v4.app.Fragment;
  19. import android.util.Log;
  20. import android.view.LayoutInflater;
  21. import android.view.MotionEvent;
  22. import android.view.SurfaceHolder;
  23. import android.view.SurfaceView;
  24. import android.view.View;
  25. import android.view.ViewGroup;
  26. import android.view.animation.ScaleAnimation;
  27. import android.widget.FrameLayout;
  28. import android.widget.ImageView;
  29. import android.widget.Toast;
  30. import com.wj.shoes.R;
  31. import com.wj.shoes.common.MyApplication;
  32. import com.wj.shoes.shortvideo.utils.ImageUtils;
  33. import com.wj.shoes.shortvideo.utils.camera.CameraHelper;
  34. import com.wj.shoes.shortvideo.utils.camera.FileUtils;
  35. import com.wj.shoes.shortvideo.utils.camera.IOUtil;
  36. import com.wj.shoes.shortvideo.utils.camera.StringUtils;
  37. import com.wj.shoes.shortvideo.view.activity.shortvideo.circle_activity_camera_sticker.CircleCameraStickerActivity;
  38. import java.io.ByteArrayInputStream;
  39. import java.io.IOException;
  40. import java.io.InputStream;
  41. import java.lang.reflect.Method;
  42. import java.util.ArrayList;
  43. import java.util.Collections;
  44. import java.util.Comparator;
  45. import java.util.Iterator;
  46. import java.util.List;
  47. import butterknife.ButterKnife;
  48. /**
  49. * 照相
  50. */
  51. public class PhotoFragment extends Fragment implements View.OnClickListener, View.OnTouchListener{
  52. private View mView;
  53. //预览画面
  54. private SurfaceView sfv_show_frame;
  55. //拍照
  56. private ImageView iv_photograph;
  57. //切换摄像头
  58. private ImageView iv_switch_camera;
  59. //切换闪光灯模式
  60. private ImageView iv_flash_lamp;
  61. private CameraHelper mCameraHelper;
  62. private View v_focus_index;
  63. private Camera cameraInst = null;
  64. private Camera.Parameters parameters = null;
  65. private int PHOTO_SIZE = 2000;
  66. //1是前置 0是后置
  67. private int mCurrentCameraId = 0;
  68. private Bundle bundle = null;
  69. //前后置摄像头切换
  70. private float pointX, pointY;
  71. static final int FOCUS = 1;// 聚焦
  72. static final int ZOOM = 2;// 缩放
  73. private int mode; //0是聚焦 1是放大
  74. private float dist;
  75. private Handler handler = new Handler();
  76. private SurfaceHolder surfaceHolder=null;
  77. private SurfaceCallback surfaceCallback=null;
  78. @Nullable
  79. @Override
  80. public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
  81. if (mView == null) {
  82. mView = inflater.inflate(R.layout.mgx_fragment_photo, container, false);
  83. mCameraHelper = new CameraHelper(getActivity());
  84. checkCameraHardware(getActivity());
  85. }
  86. return mView;
  87. }
  88. //检查该设备是否有摄像头
  89. private boolean checkCameraHardware(Context context) {
  90. if (context.getPackageManager().hasSystemFeature(PackageManager.FEATURE_CAMERA)) {
  91. initView();
  92. return true;
  93. } else {
  94. Toast.makeText(getActivity(), "该设备没有摄像头", Toast.LENGTH_LONG).show();
  95. return false;
  96. }
  97. }
  98. private void initView() {
  99. sfv_show_frame = (SurfaceView) mView.findViewById(R.id.sfv_show_frame);
  100. sfv_show_frame.setOnTouchListener(this);
  101. sfv_show_frame.setOnClickListener(this);
  102. iv_photograph = (ImageView) mView.findViewById(R.id.iv_photograph);
  103. iv_photograph.setOnClickListener(this);
  104. iv_switch_camera = (ImageView) mView.findViewById(R.id.iv_switch_camera);
  105. iv_switch_camera.setOnClickListener(this);
  106. iv_flash_lamp = (ImageView) mView.findViewById(R.id.iv_flash_lamp);
  107. iv_flash_lamp.setOnClickListener(this);
  108. v_focus_index = (View) mView.findViewById(R.id.v_focus_index);
  109. v_focus_index.setOnClickListener(this);
  110. //初始化相机
  111. surfaceHolder = sfv_show_frame.getHolder();
  112. surfaceHolder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS);
  113. surfaceHolder.setKeepScreenOn(true);
  114. sfv_show_frame.setFocusable(true);
  115. //TRIM_MEMORY_BACKGROUND ComponentCallbacks2 TRIM_MEMORY_BACKGROUND=40
  116. sfv_show_frame.setBackgroundColor(40);
  117. SurfaceCallback surfaceCallback=new SurfaceCallback();
  118. //为SurfaceView的句柄添加一个回调函数
  119. sfv_show_frame.getHolder().addCallback(surfaceCallback);
  120. }
  121. @Override
  122. public void onClick(View v) {
  123. switch (v.getId()) {
  124. //拍照
  125. case R.id.iv_photograph:
  126. cameraInst.takePicture(null, null, new MyPictureCallback());
  127. break;
  128. //切换摄像头
  129. case R.id.iv_switch_camera:
  130. switchCamera();
  131. break;
  132. //切换闪光灯
  133. case R.id.iv_flash_lamp:
  134. turnLight(cameraInst);
  135. break;
  136. //点击显示画面
  137. case R.id.sfv_show_frame:
  138. focusFrame();
  139. break;
  140. }
  141. }
  142. //聚焦框
  143. private void focusFrame() {
  144. try {
  145. pointFocus((int) pointX, (int) pointY);
  146. } catch (Exception e) {
  147. e.printStackTrace();
  148. }
  149. FrameLayout.LayoutParams layout = new FrameLayout.LayoutParams(v_focus_index.getLayoutParams());
  150. layout.setMargins((int) pointX - 60, (int) pointY - 60, 0, 0);
  151. //surface view初始化时大小的设置
  152. v_focus_index.setLayoutParams(layout);
  153. v_focus_index.setVisibility(View.VISIBLE);
  154. ScaleAnimation sa = new ScaleAnimation(3f, 1f, 3f, 1f, ScaleAnimation.RELATIVE_TO_SELF, 0.5f, ScaleAnimation.RELATIVE_TO_SELF, 0.5f);
  155. sa.setDuration(800);
  156. v_focus_index.startAnimation(sa);
  157. handler.postDelayed(new Runnable() {
  158. @Override
  159. public void run() {
  160. v_focus_index.setVisibility(View.INVISIBLE);
  161. }
  162. }, 800);
  163. }
  164. /**
  165. * 缩放
  166. *
  167. * @param view
  168. * @param motionEvent
  169. * @return
  170. */
  171. @Override
  172. public boolean onTouch(View view, MotionEvent motionEvent) {
  173. switch (motionEvent.getAction() & MotionEvent.ACTION_MASK) {
  174. // 主点按下
  175. case MotionEvent.ACTION_DOWN:
  176. pointX = motionEvent.getX();
  177. pointY = motionEvent.getY();
  178. mode = FOCUS;
  179. break;
  180. // 副点按下
  181. case MotionEvent.ACTION_POINTER_DOWN:
  182. dist = spacing(motionEvent);
  183. // 如果连续两点距离大于10,则判定为多点模式
  184. if (spacing(motionEvent) > 10f) {
  185. mode = ZOOM;
  186. }
  187. break;
  188. case MotionEvent.ACTION_UP:
  189. case MotionEvent.ACTION_POINTER_UP:
  190. mode = FOCUS;
  191. break;
  192. case MotionEvent.ACTION_MOVE:
  193. if (mode == FOCUS) {
  194. //pointFocus((int) event.getRawX(), (int) event.getRawY());
  195. } else if (mode == ZOOM) {
  196. float newDist = spacing(motionEvent);
  197. if (newDist > 10f) {
  198. float tScale = (newDist - dist) / dist;
  199. if (tScale < 0) {
  200. tScale = tScale * 10;
  201. }
  202. addZoomIn((int) tScale);
  203. }
  204. }
  205. break;
  206. }
  207. return false;
  208. }
  209. /**
  210. * 两点的距离
  211. */
  212. private float spacing(MotionEvent event) {
  213. if (event == null) {
  214. return 0;
  215. }
  216. float x = event.getX(0) - event.getX(1);
  217. float y = event.getY(0) - event.getY(1);
  218. return (float) Math.sqrt(x * x + y * y);
  219. }
  220. //放大缩小
  221. int curZoomValue = 0;
  222. private void addZoomIn(int delta) {
  223. try {
  224. Camera.Parameters params = cameraInst.getParameters();
  225. Log.d("Camera", "Is support Zoom " + params.isZoomSupported());
  226. if (!params.isZoomSupported()) {
  227. return;
  228. }
  229. curZoomValue += delta;
  230. if (curZoomValue < 0) {
  231. curZoomValue = 0;
  232. } else if (curZoomValue > params.getMaxZoom()) {
  233. curZoomValue = params.getMaxZoom();
  234. }
  235. if (!params.isSmoothZoomSupported()) {
  236. params.setZoom(curZoomValue);
  237. cameraInst.setParameters(params);
  238. return;
  239. } else {
  240. cameraInst.startSmoothZoom(curZoomValue);
  241. }
  242. } catch (Exception e) {
  243. e.printStackTrace();
  244. }
  245. }
  246. //定点对焦的代码
  247. private void pointFocus(int x, int y) {
  248. cameraInst.cancelAutoFocus();
  249. parameters = cameraInst.getParameters();
  250. if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.ICE_CREAM_SANDWICH) {
  251. showPoint(x, y);
  252. }
  253. cameraInst.setParameters(parameters);
  254. autoFocus();
  255. }
  256. @TargetApi(Build.VERSION_CODES.ICE_CREAM_SANDWICH)
  257. private void showPoint(int x, int y) {
  258. if (parameters.getMaxNumMeteringAreas() > 0) {
  259. List<Camera.Area> areas = new ArrayList<Camera.Area>();
  260. //xy变换了
  261. int rectY = -x * 2000 / MyApplication.getApp().getScreenWidth() + 1000;
  262. int rectX = y * 2000 / MyApplication.getApp().getScreenHeight() - 1000;
  263. int left = rectX < -900 ? -1000 : rectX - 100;
  264. int top = rectY < -900 ? -1000 : rectY - 100;
  265. int right = rectX > 900 ? 1000 : rectX + 100;
  266. int bottom = rectY > 900 ? 1000 : rectY + 100;
  267. Rect area1 = new Rect(left, top, right, bottom);
  268. areas.add(new Camera.Area(area1, 800));
  269. parameters.setMeteringAreas(areas);
  270. }
  271. parameters.setFocusMode(Camera.Parameters.FOCUS_MODE_CONTINUOUS_PICTURE);
  272. }
  273. @Override
  274. public void onDestroyView() {
  275. super.onDestroyView();
  276. ButterKnife.unbind(this);
  277. }
  278. private final class MyPictureCallback implements Camera.PictureCallback {
  279. @Override
  280. public void onPictureTaken(byte[] data, Camera camera) {
  281. bundle = new Bundle();
  282. //将图片字节数据保存在bundle当中,实现数据交换
  283. bundle.putByteArray("bytes", data);
  284. new SavePicTask(data).execute();
  285. // 拍完照后,重新开始预览
  286. camera.startPreview();
  287. }
  288. }
  289. /**
  290. * 异步线程更新图片
  291. */
  292. private class SavePicTask extends AsyncTask<Void, Void, String> {
  293. private byte[] data;
  294. protected void onPreExecute() {
  295. Log.d(TAG, "onPreExecute: ------------处理中------------");
  296. }
  297. //拍摄完成后的照片
  298. SavePicTask(byte[] data) {
  299. this.data = data;
  300. }
  301. @Override
  302. protected String doInBackground(Void... params) {
  303. try {
  304. return saveToSDCard(data);
  305. } catch (IOException e) {
  306. e.printStackTrace();
  307. return null;
  308. }
  309. }
  310. @Override
  311. protected void onPostExecute(String result) {
  312. super.onPostExecute(result);
  313. if (StringUtils.isNotEmpty(result)) {
  314. } else {
  315. Toast.makeText(getActivity(), "拍照失败,请稍后重试!", Toast.LENGTH_SHORT).show();
  316. }
  317. }
  318. }
  319. /**
  320. * SurfaceCallback
  321. */
  322. private final class SurfaceCallback implements SurfaceHolder.Callback {
  323. public void surfaceDestroyed(SurfaceHolder holder) {
  324. try {
  325. if (cameraInst != null) {
  326. //停止预览
  327. cameraInst.stopPreview();
  328. cameraInst.release();
  329. cameraInst = null;
  330. }
  331. } catch (Exception e) {
  332. //相机已经关了
  333. }
  334. }
  335. @Override
  336. public void surfaceCreated(SurfaceHolder holder) {
  337. if (null == cameraInst) {
  338. try {
  339. cameraInst = Camera.open();
  340. cameraInst.setPreviewDisplay(holder);
  341. initCamera();
  342. cameraInst.startPreview();
  343. } catch (Throwable e) {
  344. e.printStackTrace();
  345. }
  346. }
  347. }
  348. //屏幕发生变化时进行调用
  349. @Override
  350. public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
  351. autoFocus();
  352. }
  353. }
  354. //实现自动对焦
  355. private void autoFocus() {
  356. new Thread() {
  357. @Override
  358. public void run() {
  359. try {
  360. sleep(100);
  361. } catch (InterruptedException e) {
  362. e.printStackTrace();
  363. }
  364. if (cameraInst == null) {
  365. return;
  366. }
  367. cameraInst.autoFocus(new Camera.AutoFocusCallback() {
  368. @Override
  369. public void onAutoFocus(boolean success, Camera camera) {
  370. if (success) {
  371. //实现相机的参数初始化
  372. initCamera();
  373. }
  374. }
  375. });
  376. }
  377. };
  378. }
  379. /**
  380. * 获取相机的预览尺寸
  381. */
  382. private Camera.Size adapterSize = null;
  383. private Camera.Size previewSize = null;
  384. private void initCamera() {
  385. parameters = cameraInst.getParameters();
  386. parameters.setPictureFormat(PixelFormat.JPEG);
  387. //if (adapterSize == null) {
  388. setUpPicSize(parameters);
  389. setUpPreviewSize(parameters);
  390. //}
  391. if (adapterSize != null) {
  392. parameters.setPictureSize(previewSize.width, previewSize.height);
  393. }
  394. //设置比例尺寸
  395. if (previewSize != null) {
  396. parameters.setPreviewSize(previewSize.width, previewSize.height);
  397. }
  398. if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.ICE_CREAM_SANDWICH) {
  399. //1连续对焦
  400. parameters.setFocusMode(Camera.Parameters.FOCUS_MODE_CONTINUOUS_PICTURE);
  401. } else {
  402. parameters.setFocusMode(Camera.Parameters.FOCUS_MODE_AUTO);
  403. }
  404. setDispaly(parameters, cameraInst);
  405. try {
  406. cameraInst.setParameters(parameters);
  407. } catch (Exception e) {
  408. e.printStackTrace();
  409. }
  410. cameraInst.startPreview();
  411. // 2如果要实现连续的自动对焦,这一句必须加上
  412. cameraInst.cancelAutoFocus();
  413. }
  414. private void setUpPicSize(Camera.Parameters parameters) {
  415. if (adapterSize != null) {
  416. return;
  417. } else {
  418. adapterSize = findBestPictureResolution();
  419. return;
  420. }
  421. }
  422. private void setUpPreviewSize(Camera.Parameters parameters) {
  423. if (previewSize != null) {
  424. return;
  425. } else {
  426. previewSize = findBestPreviewResolution();
  427. }
  428. }
  429. /**
  430. * 最小预览界面的分辨率
  431. */
  432. private static final int MIN_PREVIEW_PIXELS = 480 * 320;
  433. /**
  434. * 最大宽高比差
  435. */
  436. private static final double MAX_ASPECT_DISTORTION = 0.15;
  437. private static final String TAG = "Camera";
  438. /**
  439. * 找出最适合的预览界面分辨率
  440. */
  441. private Camera.Size findBestPreviewResolution() {
  442. Camera.Parameters cameraParameters = cameraInst.getParameters();
  443. Camera.Size defaultPreviewResolution = cameraParameters.getPreviewSize();
  444. List<Camera.Size> rawSupportedSizes = cameraParameters.getSupportedPreviewSizes();
  445. if (rawSupportedSizes == null) {
  446. return defaultPreviewResolution;
  447. }
  448. // 按照分辨率从大到小排序
  449. List<Camera.Size> supportedPreviewResolutions = new ArrayList<Camera.Size>(rawSupportedSizes);
  450. Collections.sort(supportedPreviewResolutions, new Comparator<Camera.Size>() {
  451. @Override
  452. public int compare(Camera.Size a, Camera.Size b) {
  453. int aPixels = a.height * a.width;
  454. int bPixels = b.height * b.width;
  455. if (bPixels < aPixels) {
  456. return -1;
  457. }
  458. if (bPixels > aPixels) {
  459. return 1;
  460. }
  461. return 0;
  462. }
  463. });
  464. StringBuilder previewResolutionSb = new StringBuilder();
  465. for (Camera.Size supportedPreviewResolution : supportedPreviewResolutions) {
  466. previewResolutionSb.append(supportedPreviewResolution.width).append('x').append(supportedPreviewResolution.height).append(' ');
  467. }
  468. Log.v(TAG, "Supported preview resolutions: " + previewResolutionSb);
  469. // 移除不符合条件的分辨率
  470. double screenAspectRatio = (double) MyApplication.getApp().getScreenWidth() / (double) MyApplication.getApp().getScreenHeight();
  471. Iterator<Camera.Size> it = supportedPreviewResolutions.iterator();
  472. while (it.hasNext()) {
  473. Camera.Size supportedPreviewResolution = it.next();
  474. int width = supportedPreviewResolution.width;
  475. int height = supportedPreviewResolution.height;
  476. // 移除低于下限的分辨率,尽可能取高分辨率
  477. if (width * height < MIN_PREVIEW_PIXELS) {
  478. it.remove();
  479. continue;
  480. }
  481. // 在camera分辨率与屏幕分辨率宽高比不相等的情况下,找出差距最小的一组分辨率
  482. // 由于camera的分辨率是width>height,我们设置的portrait模式中,width<height
  483. // 因此这里要先交换然preview宽高比后在比较
  484. boolean isCandidatePortrait = width > height;
  485. int maybeFlippedWidth = isCandidatePortrait ? height : width;
  486. int maybeFlippedHeight = isCandidatePortrait ? width : height;
  487. double aspectRatio = (double) maybeFlippedWidth / (double) maybeFlippedHeight;
  488. double distortion = Math.abs(aspectRatio - screenAspectRatio);
  489. if (distortion > MAX_ASPECT_DISTORTION) {
  490. it.remove();
  491. continue;
  492. }
  493. // 找到与屏幕分辨率完全匹配的预览界面分辨率直接返回
  494. if (maybeFlippedWidth == MyApplication.getApp().getScreenWidth() && maybeFlippedHeight == MyApplication.getApp().getScreenHeight()) {
  495. return supportedPreviewResolution;
  496. }
  497. }
  498. // 如果没有找到合适的,并且还有候选的像素,则设置其中最大比例的,对于配置比较低的机器不太合适
  499. if (!supportedPreviewResolutions.isEmpty()) {
  500. Camera.Size largestPreview = supportedPreviewResolutions.get(0);
  501. return largestPreview;
  502. }
  503. // 没有找到合适的,就返回默认的
  504. return defaultPreviewResolution;
  505. }
  506. private Camera.Size findBestPictureResolution() {
  507. Camera.Parameters cameraParameters = cameraInst.getParameters();
  508. // 至少会返回一个值
  509. List<Camera.Size> supportedPicResolutions = cameraParameters.getSupportedPictureSizes();
  510. StringBuilder picResolutionSb = new StringBuilder();
  511. for (Camera.Size supportedPicResolution : supportedPicResolutions) {
  512. picResolutionSb.append(supportedPicResolution.width).append('x')
  513. .append(supportedPicResolution.height).append(" ");
  514. }
  515. Log.d(TAG, "Supported picture resolutions: " + picResolutionSb);
  516. Camera.Size defaultPictureResolution = cameraParameters.getPictureSize();
  517. Log.d(TAG, "default picture resolution " + defaultPictureResolution.width + "x" + defaultPictureResolution.height);
  518. // 排序
  519. List<Camera.Size> sortedSupportedPicResolutions = new ArrayList<Camera.Size>(supportedPicResolutions);
  520. Collections.sort(sortedSupportedPicResolutions, new Comparator<Camera.Size>() {
  521. @Override
  522. public int compare(Camera.Size a, Camera.Size b) {
  523. int aPixels = a.height * a.width;
  524. int bPixels = b.height * b.width;
  525. if (bPixels < aPixels) {
  526. return -1;
  527. }
  528. if (bPixels > aPixels) {
  529. return 1;
  530. }
  531. return 0;
  532. }
  533. });
  534. // 移除不符合条件的分辨率
  535. double screenAspectRatio = (double) MyApplication.getApp().getScreenWidth() / (double) MyApplication.getApp().getScreenHeight();
  536. Iterator<Camera.Size> it = sortedSupportedPicResolutions.iterator();
  537. while (it.hasNext()) {
  538. Camera.Size supportedPreviewResolution = it.next();
  539. int width = supportedPreviewResolution.width;
  540. int height = supportedPreviewResolution.height;
  541. // 在camera分辨率与屏幕分辨率宽高比不相等的情况下,找出差距最小的一组分辨率
  542. // 由于camera的分辨率是width>height,我们设置的portrait模式中,width<height
  543. // 因此这里要先交换然后在比较宽高比
  544. boolean isCandidatePortrait = width > height;
  545. int maybeFlippedWidth = isCandidatePortrait ? height : width;
  546. int maybeFlippedHeight = isCandidatePortrait ? width : height;
  547. double aspectRatio = (double) maybeFlippedWidth / (double) maybeFlippedHeight;
  548. double distortion = Math.abs(aspectRatio - screenAspectRatio);
  549. if (distortion > MAX_ASPECT_DISTORTION) {
  550. it.remove();
  551. continue;
  552. }
  553. }
  554. // 如果没有找到合适的,并且还有候选的像素,对于照片,则取其中最大比例的,而不是选择与屏幕分辨率相同的
  555. if (!sortedSupportedPicResolutions.isEmpty()) {
  556. return sortedSupportedPicResolutions.get(0);
  557. }
  558. // 没有找到合适的,就返回默认的
  559. return defaultPictureResolution;
  560. }
  561. //控制图像的正确显示方向
  562. private void setDispaly(Camera.Parameters parameters, Camera camera) {
  563. if (Build.VERSION.SDK_INT >= 8) {
  564. setDisplayOrientation(camera, 90);
  565. } else {
  566. parameters.setRotation(90);
  567. }
  568. }
  569. //实现的图像的正确显示
  570. private void setDisplayOrientation(Camera camera, int i) {
  571. Method downPolymorphic;
  572. try {
  573. downPolymorphic = camera.getClass().getMethod("setDisplayOrientation",
  574. new Class[]{int.class});
  575. if (downPolymorphic != null) {
  576. downPolymorphic.invoke(camera, new Object[]{i});
  577. }
  578. } catch (Exception e) {
  579. Log.e("Came_e", "图像出错");
  580. }
  581. }
  582. /**
  583. * 将拍下来的照片存放在SD卡中
  584. *
  585. * @param data
  586. * @throws IOException
  587. */
  588. public String saveToSDCard(byte[] data) throws IOException {
  589. Bitmap croppedImage;
  590. //获得图片大小
  591. BitmapFactory.Options options = new BitmapFactory.Options();
  592. options.inJustDecodeBounds = true;
  593. BitmapFactory.decodeByteArray(data, 0, data.length, options);
  594. PHOTO_SIZE = options.outHeight > options.outWidth ? options.outWidth : options.outHeight;
  595. int height = options.outHeight > options.outWidth ? options.outHeight : options.outWidth;
  596. options.inJustDecodeBounds = false;
  597. Rect r;
  598. if (mCurrentCameraId == 1) {
  599. r = new Rect(height - PHOTO_SIZE, 0, height, PHOTO_SIZE);
  600. } else {
  601. r = new Rect(0, 0, PHOTO_SIZE, PHOTO_SIZE);
  602. }
  603. try {
  604. croppedImage = decodeRegionCrop(data, r);
  605. } catch (Exception e) {
  606. return null;
  607. }
  608. //照片存放的路径
  609. String imagePath = ImageUtils.saveToFile(FileUtils.getInst().getSystemPhotoPath(), true, croppedImage);
  610. croppedImage.recycle();
  611. //拍好的照片带入到CircleCameraStickerActivity
  612. Intent intent = new Intent(getActivity(), CircleCameraStickerActivity.class);
  613. intent.putExtra("photoImage", imagePath);
  614. startActivity(intent);
  615. return imagePath;
  616. }
  617. private Bitmap decodeRegionCrop(byte[] data, Rect rect) {
  618. InputStream is = null;
  619. System.gc();
  620. Bitmap croppedImage = null;
  621. try {
  622. is = new ByteArrayInputStream(data);
  623. BitmapRegionDecoder decoder = BitmapRegionDecoder.newInstance(is, false);
  624. try {
  625. croppedImage = decoder.decodeRegion(rect, new BitmapFactory.Options());
  626. } catch (IllegalArgumentException e) {
  627. }
  628. } catch (Throwable e) {
  629. e.printStackTrace();
  630. } finally {
  631. IOUtil.closeStream(is);
  632. }
  633. Matrix m = new Matrix();
  634. m.setRotate(90, PHOTO_SIZE / 2, PHOTO_SIZE / 2);
  635. if (mCurrentCameraId == 1) {
  636. m.postScale(1, -1);
  637. }
  638. Bitmap rotatedImage = Bitmap.createBitmap(croppedImage, 0, 0, PHOTO_SIZE, PHOTO_SIZE, m, true);
  639. if (rotatedImage != croppedImage)
  640. croppedImage.recycle();
  641. return rotatedImage;
  642. }
  643. /**
  644. * 闪光灯开关 开->关->自动
  645. *
  646. * @param mCamera
  647. */
  648. private void turnLight(Camera mCamera) {
  649. if (mCamera == null || mCamera.getParameters() == null
  650. || mCamera.getParameters().getSupportedFlashModes() == null) {
  651. return;
  652. }
  653. Camera.Parameters parameters = mCamera.getParameters();
  654. String flashMode = mCamera.getParameters().getFlashMode();
  655. List<String> supportedModes = mCamera.getParameters().getSupportedFlashModes();
  656. if (Camera.Parameters.FLASH_MODE_OFF.equals(flashMode)
  657. && supportedModes.contains(Camera.Parameters.FLASH_MODE_ON)) {//关闭状态
  658. parameters.setFlashMode(Camera.Parameters.FLASH_MODE_ON);
  659. mCamera.setParameters(parameters);
  660. iv_flash_lamp.setImageResource(R.mipmap.mgx_camera_open_flash_lamp);
  661. } else if (Camera.Parameters.FLASH_MODE_ON.equals(flashMode)) {//开启状态
  662. if (supportedModes.contains(Camera.Parameters.FLASH_MODE_AUTO)) {
  663. parameters.setFlashMode(Camera.Parameters.FLASH_MODE_AUTO);
  664. iv_flash_lamp.setImageResource(R.mipmap.mgx_camera_auto_flash_lamp);
  665. mCamera.setParameters(parameters);
  666. } else if (supportedModes.contains(Camera.Parameters.FLASH_MODE_OFF)) {
  667. parameters.setFlashMode(Camera.Parameters.FLASH_MODE_OFF);
  668. iv_flash_lamp.setImageResource(R.mipmap.mgx_camera_close_flash_lamp);
  669. mCamera.setParameters(parameters);
  670. }
  671. } else if (Camera.Parameters.FLASH_MODE_AUTO.equals(flashMode)
  672. && supportedModes.contains(Camera.Parameters.FLASH_MODE_OFF)) {
  673. parameters.setFlashMode(Camera.Parameters.FLASH_MODE_OFF);
  674. mCamera.setParameters(parameters);
  675. iv_flash_lamp.setImageResource(R.mipmap.mgx_camera_close_flash_lamp);
  676. }
  677. }
  678. //切换前后置摄像头
  679. private void switchCamera() {
  680. mCurrentCameraId = (mCurrentCameraId + 1) % mCameraHelper.getNumberOfCameras();
  681. releaseCamera();
  682. Log.d("DDDD", "DDDD----mCurrentCameraId" + mCurrentCameraId);
  683. setUpCamera(mCurrentCameraId);
  684. }
  685. /**
  686. * 释放摄像头
  687. */
  688. public void releaseCamera() {
  689. if (cameraInst != null) {
  690. //停止预览
  691. cameraInst.stopPreview();
  692. cameraInst.release();
  693. surfaceHolder.removeCallback(surfaceCallback);
  694. cameraInst = null;
  695. }
  696. }
  697. /**
  698. * 开始预览
  699. */
  700. public void tartPreview() {
  701. if (null == cameraInst) {
  702. try {
  703. cameraInst = Camera.open();
  704. cameraInst.setPreviewDisplay(sfv_show_frame.getHolder());
  705. initCamera();
  706. cameraInst.startPreview();
  707. } catch (Throwable e) {
  708. e.printStackTrace();
  709. }
  710. }
  711. }
  712. /**
  713. * @param mCurrentCameraId2
  714. */
  715. private void setUpCamera(int mCurrentCameraId2) {
  716. cameraInst = getCameraInstance(mCurrentCameraId2);
  717. if (cameraInst != null) {
  718. try {
  719. cameraInst.setPreviewDisplay(sfv_show_frame.getHolder());
  720. initCamera();
  721. cameraInst.startPreview();
  722. } catch (IOException e) {
  723. e.printStackTrace();
  724. }
  725. } else {
  726. Log.d(TAG, "setUpCamera: -------切换失败,请重试!---------");
  727. }
  728. }
  729. /**
  730. * 获取摄像头的id
  731. *
  732. * @param id
  733. * @return
  734. */
  735. private Camera getCameraInstance(final int id) {
  736. Camera c = null;
  737. try {
  738. c = mCameraHelper.openCamera(id);
  739. } catch (Exception e) {
  740. e.printStackTrace();
  741. }
  742. return c;
  743. }
  744. }
  1. package com.wj.shoes.shortvideo.utils.camera;
  2. import android.app.Activity;
  3. import android.content.Context;
  4. import android.hardware.Camera;
  5. import android.view.Surface;
  6. import static android.os.Build.VERSION.SDK_INT;
  7. import static android.os.Build.VERSION_CODES.GINGERBREAD;
  8. /**
  9. * Created by A-23 on 2018/6/9.
  10. */
  11. public class CameraHelper {
  12. private final CameraHelperImpl mImpl;
  13. public CameraHelper(final Context context) {
  14. if (SDK_INT >= GINGERBREAD) {
  15. mImpl = new CameraHelperGB();
  16. } else {
  17. mImpl = new CameraHelperBase(context);
  18. }
  19. }
  20. public interface CameraHelperImpl {
  21. int getNumberOfCameras();
  22. Camera openCamera(int id);
  23. Camera openDefaultCamera();
  24. Camera openCameraFacing(int facing);
  25. boolean hasCamera(int cameraFacingFront);
  26. void getCameraInfo(int cameraId, CameraInfo2 cameraInfo);
  27. }
  28. public int getNumberOfCameras() {
  29. return mImpl.getNumberOfCameras();
  30. }
  31. public Camera openCamera(final int id) {
  32. return mImpl.openCamera(id);
  33. }
  34. public Camera openDefaultCamera() {
  35. return mImpl.openDefaultCamera();
  36. }
  37. public Camera openFrontCamera() {
  38. return mImpl.openCameraFacing(Camera.CameraInfo.CAMERA_FACING_FRONT);
  39. }
  40. public Camera openBackCamera() {
  41. return mImpl.openCameraFacing(Camera.CameraInfo.CAMERA_FACING_BACK);
  42. }
  43. public boolean hasFrontCamera() {
  44. return mImpl.hasCamera(Camera.CameraInfo.CAMERA_FACING_FRONT);
  45. }
  46. public boolean hasBackCamera() {
  47. return mImpl.hasCamera(Camera.CameraInfo.CAMERA_FACING_BACK);
  48. }
  49. public void getCameraInfo(final int cameraId, final CameraInfo2 cameraInfo) {
  50. mImpl.getCameraInfo(cameraId, cameraInfo);
  51. }
  52. public void setCameraDisplayOrientation(final Activity activity, final int cameraId,
  53. final Camera camera) {
  54. int result = getCameraDisplayOrientation(activity, cameraId);
  55. camera.setDisplayOrientation(result);
  56. }
  57. public int getCameraDisplayOrientation(final Activity activity, final int cameraId) {
  58. int rotation = activity.getWindowManager().getDefaultDisplay().getRotation();
  59. int degrees = 0;
  60. switch (rotation) {
  61. case Surface.ROTATION_0:
  62. degrees = 0;
  63. break;
  64. case Surface.ROTATION_90:
  65. degrees = 90;
  66. break;
  67. case Surface.ROTATION_180:
  68. degrees = 180;
  69. break;
  70. case Surface.ROTATION_270:
  71. degrees = 270;
  72. break;
  73. }
  74. int result;
  75. CameraInfo2 info = new CameraInfo2();
  76. getCameraInfo(cameraId, info);
  77. if (info.facing == Camera.CameraInfo.CAMERA_FACING_FRONT) {
  78. result = (info.orientation + degrees) % 360;
  79. } else { // back-facing
  80. result = (info.orientation - degrees + 360) % 360;
  81. }
  82. return result;
  83. }
  84. public static class CameraInfo2 {
  85. public int facing;
  86. public int orientation;
  87. }
  88. }

 

 

 

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/小小林熬夜学编程/article/detail/236015
推荐阅读
相关标签
  

闽ICP备14008679号