Closed scifinder closed 7 years ago
I answer myself =)
How can I test what photo resolutions are supported on the user's device?
CapabilitiesResult result = fotoapparat.getCapabilities(); result.toPendingResult().whenAvailable(new PendingResult.Callback<Capabilities>(){ @Override public void onResult(Capabilities capabilities){ Log.d("MY_", capabilities.supportedPictureSizes().toString()); } });
Hey!
1) You can call fa. getCapabilities()
to see what capabilities your device supports. You found it already :)
2) Please see here you need, CENTER_CROP: https://developer.android.com/reference/android/widget/ImageView.ScaleType.html
3) You can call them in resume/pause lifecycle too
4) You define the API level in your project. Usually in gradle. Here's an article about it https://medium.com/google-developers/picking-your-compilesdkversion-minsdkversion-targetsdkversion-a098a0341ebd
5) Depends your ending result wishes. Assuming that there was no orientation change, we will calculate the sensor orientation in accordance to the current display orientation. Then we will provide you with the correct degrees so as the image will be viewed upright when you apply this rotation. See the example https://github.com/Fotoapparat/Fotoapparat/blob/master/sample/src/main/java/io/fotoapparat/sample/MainActivity.java#L170
Some small corrections to @Diolor answer:
1- Normally you should select one of the sizes provided to you in Collection<Size>
- they are all supported sized. getCapabilities
is for very specific use cases and you probably do not need that.
3 - The calls have to be symmetrical and happen anywhere between onStart
and onStop
. You can even start and stop the camera several times within single screen opening.
4 - If you mean API level of Camera - we use Camera1 by default for all OS versions, because (surprise) it is more robust. You can override it if you like, but I would not recommend it.
5 - In short what @Diolor said - we give you the correct orientation, no need to account for anything else.
1 - If I want to change the resolution of the camera when it's opened, will I have to do fa.stop() => fa.photoSize(newSize).build() => fa.start()? For example, if the user has changed the resolution in the settings. How to make a "rebuild" correctly? 4 - Yes, I meant Camera API. 5 & 2 - Yeah! If I use Size.flip() according to the screen orientation, my photo will always fill the screen! =) Yes?))
1 - Either that or you can consider using FotoapparatSwitcher
. There you can just provide different versions of Fotoapparat
and then switch between them. Also, no need to expand selectors, since we already have AspectRatioSelectors
:)
You can do stuff like:
.photoSize(aspectRatio(16f/9f, biggestSize())) // Will pick the biggest 16/9 size
.photoSize(aspectRatio(4f/3f, smallestSize())) // Will pick the smallest 4/3 size
5 - You should not return size if it is not in the collection which is given to you. It can be the case that Size.flip()
is also in this collection, but it is not guaranteed for all devices.
Camera preview size actually does not affect the size of the view, it affects only resolution (aka quality of what you see on the screen). If you would like to change the size of the view, either follow @Diolor advice (and use CENTER_CROP) or change the size of the view.
Hi again! =) 1 - I did this:
.previewSize(
firstAvailable(
aspectRatio(
16f/9f,
smallestSize()
),
aspectRatio(
4f/3f,
smallestSize()
)
)
)
.photoSize(
firstAvailable(
aspectRatio(
16f/9f,
biggestSize()
),
aspectRatio(
4f/3f,
biggestSize()
)
)
)
It is right?)) 5 - I solved the problem as follows:
photoResult.toBitmap()
.whenAvailable(new PendingResult.Callback<BitmapPhoto>() {
@Override
public void onResult(BitmapPhoto result){
ImageView imageView = (ImageView) findViewById(R.id.image_view);
Matrix matrix = new Matrix();
matrix.postRotate(-result.rotationDegrees);
Bitmap bitmap = Bitmap.createBitmap(result.bitmap, 0, 0, result.bitmap.getWidth(), result.bitmap.getHeight(), matrix, false);
imageView.setImageBitmap(bitmap);
}
});
It's work correct for all screen position (image always takes full screen and have right orientation), but very slow. Are there alternatives?
@scifinder did you solved the problem related to image don't fill the entire view? If yes, how? I'm trying everything that I can imagine and even using scaleTypes it's not working.
@bruferrari, as a temporary solution, I did so. In Fotoapparat builder:
.photoSize(
firstAvailable(
aspectRatio(
16f/9f,
smallestSize()
),
aspectRatio(
4f/3f,
smallestSize()
)
)
)
In Layout:
<ImageView
android:id="@+id/image_view"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:scaleType="centerCrop" />
In takePicture():
photoResult.toBitmap()
.whenAvailable(new PendingResult.Callback<BitmapPhoto>() {
@Override
public void onResult(BitmapPhoto result){
ImageView imageView = (ImageView) findViewById(R.id.image_view);
Matrix matrix = new Matrix();
matrix.postRotate(-result.rotationDegrees);
Bitmap bitmap = Bitmap.createBitmap(result.bitmap, 0, 0, result.bitmap.getWidth(), result.bitmap.getHeight(), matrix, false);
imageView.setImageBitmap(bitmap);
}
});
It works on my tablet and phone (640x480 and 1280x720 respectively). If in photoSize() put biggestSize() value, then the matrix is processed very long (several seconds). Maybe you will offer a better solution.
@scifinder
It is right?))
Yes. You can even extract firstAvailable(...)
into a constant to not repeat yourself.
It's work correct for all screen position (image always takes full screen and have right orientation), but very slow. Are there alternatives?
You are modifying Bitmap in memory, which is not only slow but also memory consuming. The recommended way is to rotate only ImageView as it is done in the example.
@dmitry-zaitsev, @bruferrari Finally, Glide solve all my problems =)
photoResult.saveToFile(dst_file)
.whenAvailable(new PendingResult.Callback<Void>() {
@Override
public void onResult(Void t){
ImageView imageView = (ImageView) findViewById(R.id.image_view);
Glide.with(getApplicationContext()).load(dst_file).into(imageView);
}
});
Autoscale, autorotation...
Yet another option .fitCenter() (for complete lucky):
Glide.with(getApplicationContext()).load(dst_file).fitCenter().into(imageView);
Hi! =) Great work! =) I'm currently studying your library, and I have some questions.
How can I test what photo resolutions are supported on the user's device?
My code (photoResult.toBitmap().whenAvailable):
And my result: I can not fill the entire screen with the image!
Thanks!