Saya mengambil foto dan mengaturnya ke tampilan gambar.
public void captureImage() {
Intent intentCamera = new Intent("android.media.action.IMAGE_CAPTURE");
File filePhoto = new File(Environment.getExternalStorageDirectory(), "Pic.jpg");
imageUri = Uri.fromFile(filePhoto);
MyApplicationGlobal.imageUri = imageUri.getPath();
intentCamera.putExtra(MediaStore.EXTRA_OUTPUT, imageUri);
startActivityForResult(intentCamera, TAKE_PICTURE);
}
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent intentFromCamera) {
super.onActivityResult(requestCode, resultCode, intentFromCamera);
if (resultCode == RESULT_OK && requestCode == TAKE_PICTURE) {
if (intentFromCamera != null) {
Bundle extras = intentFromCamera.getExtras();
if (extras.containsKey("data")) {
bitmap = (Bitmap) extras.get("data");
}
else {
bitmap = getBitmapFromUri();
}
}
else {
bitmap = getBitmapFromUri();
}
// imageView.setImageBitmap(bitmap);
imageView.setImageURI(imageUri);
}
else {
}
}
public Bitmap getBitmapFromUri() {
getContentResolver().notifyChange(imageUri, null);
ContentResolver cr = getContentResolver();
Bitmap bitmap;
try {
bitmap = android.provider.MediaStore.Images.Media.getBitmap(cr, imageUri);
return bitmap;
}
catch (Exception e) {
e.printStackTrace();
return null;
}
}
Tapi masalahnya adalah, gambar pada beberapa perangkat setiap kali diputar. Misalnya, pada perangkat Samsung berfungsi baik, tetapi pada Sony Xperia gambar diputar sebesar 90 derajat dan pada Toshiba Thrive (tablet) sebesar 180 derajat.
Jawaban:
Sebagian besar kamera ponsel berbentuk lansekap, artinya jika Anda mengambil foto dalam potret, foto yang dihasilkan akan diputar 90 derajat. Dalam hal ini, perangkat lunak kamera harus mengisi data Exif dengan orientasi bahwa foto harus dilihat.
Perhatikan bahwa solusi di bawah ini tergantung pada produsen perangkat lunak / perangkat kamera yang mengisi data Exif, sehingga ini akan berfungsi dalam kebanyakan kasus, tetapi itu bukan solusi yang dapat diandalkan 100%.
Inilah
rotateImage
metodenya:sumber
exif.getAttributeInt
menggunakanExifInterface.ORIENTATION_UNDEFINED
hampir sama, karena parameter kedua adalah nilai default jika fungsi gagal memberikan nilai.Dengan menggabungkan Jason Robinson 's jawaban dengan Felix ' s jawaban dan mengisi bagian yang hilang, di sini adalah solusi lengkap akhir untuk masalah ini yang akan melakukan hal berikut setelah pengujian pada Android Android 4.1 ( Jelly Bean ), Android 4.4 ( KitKat ) dan Android 5.0 ( Lollipop ).
Langkah
Perkecil gambar jika lebih besar dari 1024x1024.
Putar gambar ke orientasi kanan hanya jika diputar 90, 180 atau 270 derajat.
Daur ulang gambar yang diputar untuk keperluan memori.
Inilah bagian kode:
Panggil metode berikut dengan arus
Context
dan gambarURI
yang ingin Anda perbaikiBerikut adalah
CalculateInSampleSize
metode dari sumber yang disebutkan sebelumnya :Kemudian datang metode yang akan memeriksa orientasi gambar saat ini untuk menentukan sudut rotasi
Akhirnya metode rotasi itu sendiri
-Jangan lupa untuk memilih jawaban orang-orang atas upaya mereka dan Shirish Herwade yang mengajukan pertanyaan bermanfaat ini.
sumber
Mudah untuk mendeteksi orientasi gambar dan mengganti bitmap menggunakan:
Untuk menghindari Kehabisan memori dengan gambar besar, saya sarankan Anda untuk mengubah skala gambar menggunakan:
Tidak mungkin menggunakan ExifInterface untuk mendapatkan orientasi karena masalah OS Android: https://code.google.com/p/android/issues/detail?id=19268
Dan ini dia
calculateInSampleSize
sumber
Solusi satu baris:
Atau
Ini akan mendeteksi rotasi otomatis dan menempatkan gambar dalam orientasi yang benar
Picasso adalah perpustakaan yang sangat kuat untuk menangani gambar di aplikasi Anda termasuk: Transformasi gambar yang kompleks dengan penggunaan memori minimal.
sumber
Saya telah menghabiskan banyak waktu mencari solusi untuk ini. Dan akhirnya berhasil melakukan ini. Jangan lupa untuk menjawab @Jason Robinson karena saya berdasarkan pada jawabannya.
Jadi hal pertama, Anda harus tahu bahwa sejak Android 7.0 kita harus menggunakan
FileProvider
dan sesuatu yang disebutContentUri
, jika tidak, Anda akan mendapatkan kesalahan yang mengganggu ketika mencoba memanggil AndaIntent
. Ini adalah kode contoh:Metode
getUriFromPath(Context, String)
dasar pada versi pengguna Android buatFileUri (file://...)
atauContentUri (content://...)
dan itu ada:Setelah
onActivityResult
Anda dapat menangkap bahwa diuri
mana gambar disimpan oleh kamera, tetapi sekarang Anda harus mendeteksi rotasi kamera, di sini kita akan menggunakan jawaban @Jason Robinson yang dimodifikasi:Pertama kita perlu membuat
ExifInterface
berdasarkanUri
Kode di atas dapat disederhanakan, tetapi saya ingin menunjukkan semuanya. Jadi dari
FileUri
kita dapat membuatExifInterface
berdasarkanString path
, tetapi dariContentUri
kita tidak bisa, Android tidak mendukung itu.Dalam hal ini kita harus menggunakan konstruktor lain berdasarkan
InputStream
. Ingat konstruktor ini tidak tersedia secara default, Anda harus menambahkan perpustakaan tambahan:Sekarang kita bisa menggunakan
getExifInterface
metode untuk mendapatkan sudut pandang kita:Sekarang Anda memiliki Angle untuk memutar gambar Anda dengan benar :).
sumber
activity_main.xml
MainActivity.java
sumber
Anda cukup membaca orientasi sensor kamera seperti yang ditunjukkan oleh Google dalam dokumentasi: https://developer.android.com/reference/android/hardware/camera2/CameraCharacteristics.html
Kode sampel:
sumber
Jason Robinson jawaban dan Sami Eltamawy jawabannya adalah Excellent.
Hanya peningkatan untuk menyelesaikan pendekatan, Anda harus menggunakan compat ExifInterface.
com.android.support:exifinterface:${lastLibVersion}
Anda akan dapat meng-instantiate ExifInterface (pior API <24) dengan
InputStream
(dariContentResolver
) alih-alih jalur uri menghindari "File not found exception"https://android-developers.googleblog.com/2016/12/introducing-the-exifinterface-support-library.html
sumber
Biasanya disarankan untuk menyelesaikan masalah dengan ExifInterface , seperti yang disarankan oleh @Jason Robinson. Jika pendekatan ini tidak berhasil, Anda dapat mencoba mencari Orientasi dari gambar terbaru yang diambil ...
sumber
Sayangnya, @ jason-robinson jawaban di atas tidak berhasil untuk saya.
Meskipun fungsi putar berfungsi dengan sempurna:
Saya harus melakukan yang berikut untuk mendapatkan orientasi karena orientasi Exif selalu 0
sumber
Lebih baik coba mengambil gambar dalam orientasi tertentu.
Untuk hasil terbaik, berikan orientasi lanskap dalam aktivitas tampilan kamera.
sumber
Jika seseorang mengalami masalah dengan
ExifInterface
di Android 4.4 (KitKat) untuk mendapatkan orientasi, itu mungkin karena jalur yang salah didapat dari URI. Lihat solusi untuk propoergetPath
di pertanyaan Stack Overflow Dapatkan jalur nyata dari URI, Android KitKat, kerangka akses penyimpanan barusumber
Temukan tautan di bawah solusi ini adalah https://www.samieltamawy.com/how-to-fix-the-camera-intent-rotated-image-in-android/ terbaik
sumber
Jawaban yang dipilih menggunakan metode yang paling umum dijawab untuk ini dan pertanyaan serupa. Namun, itu tidak bekerja dengan kamera depan dan belakang di Samsung. Bagi mereka yang mencari solusi yang bekerja di kedua kamera depan dan belakang untuk Samsung dan produsen besar lainnya, jawaban dari nvhausid ini luar biasa:
https://stackoverflow.com/a/18915443/6080472
Bagi mereka yang tidak ingin mengklik, sihir yang relevan adalah dengan menggunakan CameraInfo daripada mengandalkan EXIF.
Kode lengkap di tautan.
sumber
Ini mungkin tidak perlu dikatakan tetapi selalu ingat bahwa Anda dapat menangani beberapa masalah penanganan gambar ini di server Anda. Saya menggunakan tanggapan seperti yang ada di utas ini untuk menangani tampilan langsung gambar. Namun aplikasi saya membutuhkan gambar untuk disimpan di server (ini mungkin persyaratan umum jika Anda ingin gambar tetap ada sebagai pengguna beralih ponsel).
Solusi yang terkandung dalam banyak utas mengenai topik ini tidak membahas kurangnya data EXIF yang tidak bertahan dari kompresi gambar Bitmap, artinya Anda harus memutar gambar setiap kali server memuatnya. Atau, Anda dapat mengirim data orientasi EXIF ke server Anda, dan kemudian memutar gambar di sana jika diperlukan.
Lebih mudah bagi saya untuk membuat solusi permanen di server karena saya tidak perlu khawatir tentang jalur file klandestin Android.
sumber
Solusi paling sederhana untuk masalah ini:
Saya menyimpan gambar dalam format jpg.
sumber
Ini
Xamarin.Android
versinya:Dari jawaban @Jason Robinson :
Kemudian
calculateInSampleSize
metode:Dari jawaban @Sami Eltamawy :
sumber
Jika Anda menggunakan Fresco, Anda bisa menggunakan ini -
Ini secara otomatis memutar gambar berdasarkan data Exif.
Sumber: https://frescolib.org/docs/rotation.html
sumber
Kode di bawah ini bekerja dengan saya, itu mendapatkan bitmap dari fileUri, dan melakukan perbaikan rotasi jika diperlukan:
sumber
Mendapat jawaban untuk masalah ini tanpa menggunakan ExifInterface . Kita bisa mendapatkan rotasi kamera baik kamera depan atau kamera belakang mana pun yang Anda gunakan saat membuat Bitmap, kami dapat memutar bitmap menggunakan Matrix.postRotate (degree)
Setelah menghitung rotasi, Anda dapat memutar bitmap Anda seperti di bawah ini:
Herare bm harus menjadi bitmap Anda.
Jika Anda ingin mengetahui rotasi kamera depan Anda cukup ganti Camera.CameraInfo.CAMERA_FACING_BACK ke Camera.CameraInfo.CAMERA_FACING_FRONT di atas.
Saya harap ini membantu.
sumber
Saya membuat fungsi ekstensi Kotlin yang menyederhanakan operasi untuk pengembang Kotlin berdasarkan jawaban @Jason Robinson. Saya harap ini membantu.
sumber
Ada perintah yang lebih sederhana untuk memperbaiki kesalahan ini.
Cukup tambahkan setelah yourImageView.setBitmap (bitmap); ini yourImageView.setRotation (90);
Tambang ini diperbaiki. Semoga ini bisa membantu!
sumber
ini bekerja untuk saya
sumber