Fixing image orientation on mobile camera uploads
Ever run into an issue trying to fix image orientation when uploading an image that was taken with the camera on a mobile device directly Yeah, I ran into this issue this week…not fun.
After doing some research this week around the issue, I found a pretty simple solution using blueimp-load-image
package. This package handles a bunch of issues related to handling images that are taken using the camera and directly uploaded to your web app.
So let’s start with understanding the issue.
The problem
The only time you run into this specific issue is when a user tries to upload a photo taken during the user experience. The story is usually:
- User visits app
- User clicks “upload image”
- User selects camera on phone
- User takes picture
- User confirms this is the picture they want to use
If you create the image blob and set it to the source of an <img>
then you get an incorrect orientation of that image.
In my case, if I took the photo vertically - then it would appear sideways on the page.
Background on the issue
TL;DR - browsers don’t handle the EXIF data provided by the phone.
For more information you can check out this excellent resources:
EXIF Orientation Handling Is a Ghetto
JS Client-Side Exif Orientation: Rotate and Mirror JPEG Images
Handle image rotation on mobile
How does blueimp-load-image address the issue
Sebastian has done an excellent job at taking the EXIF data and auto handling these scenarios for you.
For example, Orientation
is figured out through the exif-map functionality here.
On top of figuring this out for you, they have provided an easy to use API.
Usage Example
First, install the package:
yarn add blueimp-load-image
Next, import the package int your JS:
import loadImage from "blueimp-load-image"
Finally, to ensure orientation is fixed:
const handleFileChange = ({ target: { files } }) => {
const file = files.item(0)
loadImage(
file,
img => {
document.getElementById("uploaded-image").appendChild(img)
},
{ maxWidth: 125, orientation: true }
)
}
Note that I’m setting orientation
to true
as part loadImage
’s 2nd parameter object. I’ve also included a maxWidth
of 125 for my use case. For more options, check out the docs here.
Alright folks, that’s all I have for today. If you found this helpful, have feedback or are interested in a quick chat - hit me up at @alvincrespo.