Making pictures capture in Android simple

Dionysis Lorentzos
Dionysis’ desk
Published in
3 min readJun 26, 2017
Fotoapparat’s icon by Leander Lenzing

Let’s face it. Camera api in Android is so broken. Ever talked with an iOS colleague about camera? It “just works” and it’s super frustrating for us (Android devs) to have to spend so much time, weeks to be precise, if we want to use a camera inside our app.

Dmitry has used camera extensively to know the pain and we concluded that there should be an easier way: a simple library which just works with camera in Android phones.

The idea is simple: ask the library what kind of picture you are willing to take (e.g. MPixels, flash, focus), start/stop the preview during your lifecycle and just provide the interface to take the goddamn photo. All in a simple way that lets you stay sane and have proper sleep at nights.

So here you go. We created Fotoapparat! It does what promises above and we also added some sugar like registering preview frame analyzer, proper logger, readable way to get the camera capabilities and simple parameters updating API.

Usage

What’s more simple than the following code to take a picture?

Fotoapparat fotoapparat = Fotoapparat
.with(context)
.into(cameraView)
.build();

fotoapparat.start();

fotoapparat
.takePicture()
.saveToFile(someFile);

Looks neat? Hope you like it!

Let’s dive further. How do you initialize the library?

With a readable builder. Add all the parameters you wish and we will take care of the rest:

Fotoapparat fotoapparat = Fotoapparat
.with(context)
.into(cameraView)
.lensPosition(firstAvailable(
front(), back()
))
// even more options here
.build();

Starting/stoping the preview? Easy.

@Override
protected void onStart() {
super.onStart();

fotoapparat.start();
}

@Override
protected void onStop() {
super.onStop();

fotoapparat.stop();
}

Taking pictures? Yes sir! You wish a File, a Bitmap or both?

PhotoResult photoResult = fotoapparat.takePicture();// save to file
photoResult.saveToFile(new File(
getExternalFilesDir("photos"),
"photo.jpg"
));
// obtain Bitmap
photoResult
.toBitmap()
.whenAvailable(bitmapPhoto -> {
imageView.setImageBitmap(bitmapPhoto.bitmap);
});

Blocking, callback, RxJava 1/2 (Single, Observable, Completable)? Your choice:

// synchronous
BitmapPhoto bitmapPhoto = photoResult
.toBitmap()
.await();
// asynchronous
photoResult
.toBitmap()
.whenAvailable(bitmapPhoto -> {

});
// RxJava
photoResult
.toBitmap()
.adapt(SingleAdapter.<BitmapPhoto>toSingle())
.subscribe(bitmapPhoto -> {

});

What can Fotoapparat do?

  • Start an Android camera (front, back or external)
  • Start/stop a View preview with desired resolution
  • Take a photo, with desired resolution, focus and flash
  • Obtain the frames of the preview for further processing
  • Easily obtain bitmaps or write photos to files
  • Work nicely with RxJava 1/2
  • Make you happy

What are we planning in Fotoapparat?

  • Switch cameras easily

What Fotoapparat cannot do?

  • Take videos
  • Make you coffee :(

Credits

We want to say thanks to Mark Murphy for the awesome job he did with CWAC-Camera. We were using his library for a couple of years and now we feel that Fotoapparat is a next step in the right direction.

We are also extremely thankful to our friend Leander Lenzing for his amazing work on designing our logo.

--

--

Dionysis Lorentzos
Dionysis’ desk

Dionysis is an Android dev ShareNow + Founder of Nutech, a jobs app only for Android developers. He is passionate about auto industry innovation & space