http://arabiannight.tistory.com/45
▒ ▒ ▒ ▒ ▒ ▒ ▒ 전체 소스 입니다. ▒ ▒ ▒ ▒ ▒ ▒ ▒
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 | public class TestImageCropActivity extends Activity { private static final String TAG = "TestImageCropActivity" ; private static final int PICK_FROM_CAMERA = 0 ; private static final int PICK_FROM_ALBUM = 1 ; private static final int CROP_FROM_CAMERA = 2 ; private Uri mImageCaptureUri; private AlertDialog mDialog; @Override protected void onCreate(Bundle savedInstanceState) { super .onCreate(savedInstanceState); setContentView(R.layout.main); setLayout(); } /** Button Click */ public void onButtonClick(View v){ switch (v.getId()) { case R.id.btn_sns: sendSMS( "01000000000" , "hi nice to meet you" ); break ; case R.id.btn_mms: Log.e(TAG, "mImageCaptureUri = " + mImageCaptureUri); sendMMS(mImageCaptureUri); // sendMMSG(); break ; case R.id.btn_image_crop: mDialog = createDialog(); mDialog.show(); break ; } } /** * 다이얼로그 생성 */ private AlertDialog createDialog() { final View innerView = getLayoutInflater().inflate(R.layout.image_crop_row, null ); Button camera = (Button)innerView.findViewById(R.id.btn_camera_crop); Button gellary = (Button)innerView.findViewById(R.id.btn_gellary_crop); camera.setOnClickListener( new OnClickListener() { @Override public void onClick(View v) { doTakePhotoAction(); setDismiss(mDialog); } }); gellary.setOnClickListener( new OnClickListener() { @Override public void onClick(View v) { doTakeAlbumAction(); setDismiss(mDialog); } }); AlertDialog.Builder ab = new AlertDialog.Builder( this ); ab.setTitle( "이미지 Crop" ); ab.setView(innerView); return ab.create(); } /** * 다이얼로그 종료 */ private void setDismiss(AlertDialog dialog){ if (dialog!= null &&dialog.isShowing()){ dialog.dismiss(); } } /** * SMS 발송 */ private void sendSMS(String reciver , String content){ Uri uri = Uri.parse( "smsto:" +reciver); Intent it = new Intent(Intent.ACTION_SENDTO, uri); it.putExtra( "sms_body" , content); startActivity(it); } /** * MMS 발송 (APP TAB BOX) */ private void sendMMS(Uri uri){ uri = Uri.parse( "" +uri); Intent it = new Intent(Intent.ACTION_SEND); it.putExtra( "sms_body" , "some text" ); it.putExtra(Intent.EXTRA_STREAM, uri); it.setType( "image/*" ); // 삼성 단말에서만 허용 ( 앱 선택 박스 없이 호출 ) // it.setComponent(new ComponentName("com.sec.mms", "com.sec.mms.Mms")); startActivity(it); } /** * MMS 발송 ( 첨부 파일 없음 ) */ private void sendMMSG(){ Uri mmsUri = Uri.parse( "mmsto:" ); Intent sendIntent = new Intent(Intent.ACTION_VIEW, mmsUri); sendIntent.addCategory( "android.intent.category.DEFAULT" ); sendIntent.addCategory( "android.intent.category.BROWSABLE" ); sendIntent.putExtra( "address" , "01000000000" ); sendIntent.putExtra( "exit_on_sent" , true ); sendIntent.putExtra( "subject" , "dfdfdf" ); sendIntent.putExtra( "sms_body" , "dfdfsdf" ); Uri dataUri = Uri.parse( "" +mImageCaptureUri); sendIntent.putExtra(Intent.EXTRA_STREAM, dataUri); startActivity(sendIntent); } /** * 카메라 호출 하기 */ private void doTakePhotoAction() { Log.i(TAG, "doTakePhotoAction()" ); Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE); // Crop된 이미지를 저장할 파일의 경로를 생성 mImageCaptureUri = createSaveCropFile(); intent.putExtra(android.provider.MediaStore.EXTRA_OUTPUT, mImageCaptureUri); startActivityForResult(intent, PICK_FROM_CAMERA); } /** * 앨범 호출 하기 */ private void doTakeAlbumAction() { Log.i(TAG, "doTakeAlbumAction()" ); // 앨범 호출 Intent intent = new Intent(Intent.ACTION_PICK); intent.setType(android.provider.MediaStore.Images.Media.CONTENT_TYPE); startActivityForResult(intent, PICK_FROM_ALBUM); } /** * Result Code */ @Override protected void onActivityResult( int requestCode, int resultCode, Intent data) { Log.d(TAG, "onActivityResult" ); if (resultCode != RESULT_OK) { return ; } switch (requestCode) { case PICK_FROM_ALBUM: { Log.d(TAG, "PICK_FROM_ALBUM" ); // 이후의 처리가 카메라와 같으므로 일단 break없이 진행합니다. // 실제 코드에서는 좀더 합리적인 방법을 선택하시기 바랍니다. mImageCaptureUri = data.getData(); File original_file = getImageFile(mImageCaptureUri); mImageCaptureUri = createSaveCropFile(); File cpoy_file = new File(mImageCaptureUri.getPath()); // SD카드에 저장된 파일을 이미지 Crop을 위해 복사한다. copyFile(original_file , cpoy_file); } case PICK_FROM_CAMERA: { Log.d(TAG, "PICK_FROM_CAMERA" ); // 이미지를 가져온 이후의 리사이즈할 이미지 크기를 결정합니다. // 이후에 이미지 크롭 어플리케이션을 호출하게 됩니다. Intent intent = new Intent( "com.android.camera.action.CROP" ); intent.setDataAndType(mImageCaptureUri, "image/*" ); // Crop한 이미지를 저장할 Path intent.putExtra( "output" , mImageCaptureUri); // Return Data를 사용하면 번들 용량 제한으로 크기가 큰 이미지는 // 넘겨 줄 수 없다. // intent.putExtra("return-data", true); startActivityForResult(intent, CROP_FROM_CAMERA); break ; } case CROP_FROM_CAMERA: { Log.w(TAG, "CROP_FROM_CAMERA" ); // Crop 된 이미지를 넘겨 받습니다. Log.w(TAG, "mImageCaptureUri = " + mImageCaptureUri); String full_path = mImageCaptureUri.getPath(); String photo_path = full_path.substring( 4 , full_path.length()); Log.w(TAG, "비트맵 Image path = " +photo_path); Bitmap photo = BitmapFactory.decodeFile(photo_path); mPhotoImageView.setImageBitmap(photo); break ; } } } /** * Crop된 이미지가 저장될 파일을 만든다. * @return Uri */ private Uri createSaveCropFile(){ Uri uri; String url = "tmp_" + String.valueOf(System.currentTimeMillis()) + ".jpg" ; uri = Uri.fromFile( new File(Environment.getExternalStorageDirectory(), url)); return uri; } /** * 선택된 uri의 사진 Path를 가져온다. * uri 가 null 경우 마지막에 저장된 사진을 가져온다. * @param uri * @return */ private File getImageFile(Uri uri) { String[] projection = { MediaStore.Images.Media.DATA }; if (uri == null ) { uri = MediaStore.Images.Media.EXTERNAL_CONTENT_URI; } Cursor mCursor = getContentResolver().query(uri, projection, null , null , MediaStore.Images.Media.DATE_MODIFIED + " desc" ); if (mCursor == null || mCursor.getCount() < 1 ) { return null ; // no cursor or no record } int column_index = mCursor.getColumnIndexOrThrow(MediaStore.Images.Media.DATA); mCursor.moveToFirst(); String path = mCursor.getString(column_index); if (mCursor != null ) { mCursor.close(); mCursor = null ; } return new File(path); } /** * 파일 복사 * @param srcFile : 복사할 File * @param destFile : 복사될 File * @return */ public static boolean copyFile(File srcFile, File destFile) { boolean result = false ; try { InputStream in = new FileInputStream(srcFile); try { result = copyToFile(in, destFile); } finally { in.close(); } } catch (IOException e) { result = false ; } return result; } /** * Copy data from a source stream to destFile. * Return true if succeed, return false if failed. */ private static boolean copyToFile(InputStream inputStream, File destFile) { try { OutputStream out = new FileOutputStream(destFile); try { byte [] buffer = new byte [ 4096 ]; int bytesRead; while ((bytesRead = inputStream.read(buffer)) >= 0 ) { out.write(buffer, 0 , bytesRead); } } finally { out.close(); } return true ; } catch (IOException e) { return false ; } } /* * Layout */ private ImageView mPhotoImageView; private void setLayout(){ mPhotoImageView = (ImageView)findViewById(R.id.img_bitmap); } } |
▒ ▒ ▒ ▒ ▒ ▒ ▒ 디테일 설명 입니다. ▒ ▒ ▒ ▒ ▒ ▒ ▒
▒ 1.
참고사이트 : http://theeye.pe.kr/entry/example-of-image-crop-with-camera-and-album-picker-on-android
아이군님의 블로그의 Crop소스 를 참고였습니다. 참 설명이 잘 되있어서 보기 편했는데요. 바뀐점이 있다면 Crop후 이미지를 넘기는 과정에서 번들은 사용해서 넘기셨기대문에 고화질의 사진을 Crop할 경우 Return Data를 넘기지 못하는 현상이 발생하였습니다. 그래서 Crop이 정상 작동 하지 않는 경우가 생기게 되어, 일단 File을 생성 후 그 파일을 Crop한 후 저장하는 형식으로 수정 하 였습니다. 전체적인 틀은 비슷하게 가고 나머지 부분은 약간씩 수정 되었구요. SMS와 Crop한 이미지를 전송하는 MMS 기능을 추가 하였습니다.
▒ 2.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 | case PICK_FROM_CAMERA: { Log.d(TAG, "PICK_FROM_CAMERA" ); // 이미지를 가져온 이후의 리사이즈할 이미지 크기를 결정합니다. // 이후에 이미지 크롭 어플리케이션을 호출하게 됩니다. Intent intent = new Intent( "com.android.camera.action.CROP" ); intent.setDataAndType(mImageCaptureUri, "image/*" ); // Crop한 이미지를 저장할 Path intent.putExtra( "output" , mImageCaptureUri); // Return Data를 사용하면 번들 용량 제한으로 크기가 큰 이미지는 // 넘겨 줄 수 없다. // intent.putExtra("return-data", true); startActivityForResult(intent, CROP_FROM_CAMERA); break ; } |
intent.putExtra("output", mImageCaptureUri);
아웃풋 경로 지정함으로써 Crop 된 이미지가 해당 Uri로 Ruturn 되도록 설정 하였습니다.
▒ 3.
1 2 3 4 5 6 7 8 9 10 | /** * Crop된 이미지가 저장될 파일을 만든다. * @return Uri */ private Uri createSaveCropFile(){ Uri uri; String url = "tmp_" + String.valueOf(System.currentTimeMillis()) + ".jpg" ; uri = Uri.fromFile( new File(Environment.getExternalStorageDirectory(), url)); return uri; } |
Crop이 완료된 파일은 해당 기기의 SDcard에 저장 됩니다.
▒ 4. 파일첨부 및 스크린샷.
반응형
'차근차근 > Android' 카테고리의 다른 글
[안드로이드]파일 연결 - Intent setDataAndType(Uri , MimeType) (0) | 2014.08.28 |
---|---|
Camera 호출 후 이미지 Crop하기 예제 (0) | 2014.08.28 |
안드로이드 Intent putExtra, getIntent 예제 따라하기 (0) | 2014.08.28 |
인텐트 (0) | 2014.08.28 |
카메라 크롭 기능 (Camera Crop) (0) | 2014.08.28 |