Beyka / Android-TiffBitmapFactory

MIT License
131 stars 46 forks source link

when open multiFIle, I had a question "OutOfMemoryError" #21

Closed 1049884729 closed 7 years ago

1049884729 commented 7 years ago

The Error code is ` TiffBitmapFactory.Options options = new TiffBitmapFactory.Options(); options.inJustDecodeBounds = true; options.inThrowException = true;// 调试使用 TiffBitmapFactory.decodeFile(file, options); int dirCount = options.outDirectoryCount; // Read and process all images in file for (int i = 0; i < dirCount; i++) { options.inDirectoryNumber = i; TiffBitmapFactory.decodeFile(file, options); int curDir = options.outCurDirectoryNumber; int width = options.outWidth; int height = options.outHeight; // Change sample size if width or height bigger than required width or height int inSampleSize = 1; if (height > reqHeight || width > reqWidth) {

                final int halfHeight = height / 2;
                final int halfWidth = width / 2;

                // Calculate the largest inSampleSize value that is a power of 2 and keeps both
                // height and width larger than the requested height and width.
                while ((halfHeight / inSampleSize) > reqHeight && (halfWidth / inSampleSize) > reqWidth) {
                    inSampleSize *= 2;
                }
            }
            options.inJustDecodeBounds = false;
            options.inSampleSize = inSampleSize;

            // Specify the amount of memory available for the final bitmap and temporary storage.
            options.inAvailableMemory = TiffTools.getFreeMemmory(context); // bytes

            Bitmap bmp = TiffBitmapFactory.decodeFile(file, options);
            bitmaps.add(bmp);
        }`

Quitely ,the error happened is Second TiffBitmapFactory.decodeFile(file, options);, Error Log is java.lang.IllegalStateException: Fatal Exception thrown on Scheduler.Worker thread. at rx.internal.schedulers.ScheduledAction.run(ScheduledAction.java:59) at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:422) at java.util.concurrent.FutureTask.run(FutureTask.java:237) at java.util.concurrent.ScheduledThreadPoolExecutor$ScheduledFutureTask.access$201(ScheduledThreadPoolExecutor.java:152) at java.util.concurrent.ScheduledThreadPoolExecutor$ScheduledFutureTask.run(ScheduledThreadPoolExecutor.java:265) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1112) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:587) at java.lang.Thread.run(Thread.java:818) Caused by: java.lang.OutOfMemoryError: Failed to allocate a 8355852 byte allocation with 2497147 free bytes and 2MB until OOM at dalvik.system.VMRuntime.newNonMovableArray(Native Method) at android.graphics.Bitmap.nativeCreate(Native Method) at android.graphics.Bitmap.createBitmap(Bitmap.java:812) at android.graphics.Bitmap.createBitmap(Bitmap.java:789) at android.graphics.Bitmap.createBitmap(Bitmap.java:756) at org.beyka.tiffbitmapfactory.TiffBitm java.lang.IllegalStateException: Fatal Exception thrown on Scheduler.Worker thread. at rx.internal.schedulers.ScheduledAction.run(ScheduledAction.java:59) at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:422) at java.util.concurrent.FutureTask.run(FutureTask.java:237) at java.util.concurrent.ScheduledThreadPoolExecutor$ScheduledFutureTask.access$201(ScheduledThreadPoolExecutor.java:152) at java.util.concurrent.ScheduledThreadPoolExecutor$ScheduledFutureTask.run(ScheduledThreadPoolExecutor.java:265) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1112) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:587) at java.lang.Thread.run(Thread.java:818) Caused by: java.lang.OutOfMemoryError: Failed to allocate a 8355852 byte allocation with 2497147 free bytes and 2MB until OOM at dalvik.system.VMRuntime.newNonMovableArray(Native Method) at android.graphics.Bitmap.nativeCreate(Native Method) at android.graphics.Bitmap.createBitmap(Bitmap.java:812) at android.graphics.Bitmap.createBitmap(Bitmap.java:789) at android.graphics.Bitmap.createBitmap(Bitmap.java:756) at org.beyka.tiffbitmapfactory.TiffBitmapFactory.nativeDecodePath(Native Method) at org.beyka.tiffbitmapfactory.TiffBitmapFactory.decodeFile(TiffBitmapFactory.java:96) at.TiffTools.openTiffToBitmaps(TiffTools.java:124) at .TiffTools.getFilePathListByTiff(TiffTools.java:166)apFactory.nativeDecodePath(Native Method) at org.beyka.tiffbitmapfactory.TiffBitmapFactory.decodeFile(TiffBitmapFactory.java:96) .TiffTools.openTiffToBitmaps(TiffTools.java:124) at TiffTools.getFilePathListByTiff(TiffTools.java:166)

Please help me!

Beyka commented 7 years ago

According to this error message: "Caused by: java.lang.OutOfMemoryError: Failed to allocate a 8355852 byte allocation with 2497147 free bytes and 2MB until OOM at dalvik.system.VMRuntime.newNonMovableArray(Native Method) at android.graphics.Bitmap.nativeCreate(Native Method)" Your device hasn't enough memory to create android.Bitmap object. It could be if you showing to many bitmaps on screen(for example in RecycleView) if your reqHeight and reqWidth is to large(it could be on devices with screens that bigger than FullHD) If you use some kind of adapter view - try to decrease req width and height. Any way algorithm to calculating inSampleSize is recommended algorithm by android developers web site(https://developer.android.com/topic/performance/graphics/load-bitmap.html), but you could use your own. One restriction - inSampleSize should be 1 or power of 2(1, 2, 4, 8 ...)

1049884729 commented 7 years ago

I have resolve this problem! In AndroidManifest.xml,the app need add the tag: android:largeHeap="true" Thank you sir!