diff --git a/reddinator/src/main/java/au/com/wallaceit/reddinator/core/Utilities.java b/reddinator/src/main/java/au/com/wallaceit/reddinator/core/Utilities.java index a89f134..a8eeb92 100644 --- a/reddinator/src/main/java/au/com/wallaceit/reddinator/core/Utilities.java +++ b/reddinator/src/main/java/au/com/wallaceit/reddinator/core/Utilities.java @@ -27,13 +27,7 @@ import android.content.Intent; import android.content.pm.PackageInfo; import android.content.pm.PackageManager; -import android.graphics.Bitmap; -import android.graphics.Canvas; -import android.graphics.Color; -import android.graphics.ColorMatrix; -import android.graphics.ColorMatrixColorFilter; -import android.graphics.Paint; -import android.graphics.Typeface; +import android.graphics.*; import android.net.Uri; import android.os.Build; import android.text.Html; @@ -332,4 +326,46 @@ public void onClick(DialogInterface dialog, int which) { } Toast.makeText(context, ex.getMessage(), Toast.LENGTH_LONG).show(); } + + /* + * See https://developer.android.com/topic/performance/graphics/load-bitmap + * */ + public static int calculateInSampleSize(BitmapFactory.Options options, int reqWidth, int reqHeight) { + // Raw height and width of image + final int height = options.outHeight; + final int width = options.outWidth; + 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; + } + } + + return inSampleSize; + } + + /* + * See https://developer.android.com/topic/performance/graphics/load-bitmap + * */ + public static Bitmap decodeSampledBitmapFromFile(String fileurl, int reqWidth, int reqHeight) { + + // First decode with inJustDecodeBounds=true to check dimensions + final BitmapFactory.Options options = new BitmapFactory.Options(); + options.inJustDecodeBounds = true; + BitmapFactory.decodeFile(fileurl, options); + + // Calculate inSampleSize + options.inSampleSize = calculateInSampleSize(options, reqWidth, reqHeight); + + // Decode bitmap with inSampleSize set + options.inJustDecodeBounds = false; + return BitmapFactory.decodeFile(fileurl, options); + } } diff --git a/reddinator/src/main/java/au/com/wallaceit/reddinator/ui/SubredditFeedAdapter.java b/reddinator/src/main/java/au/com/wallaceit/reddinator/ui/SubredditFeedAdapter.java index 4e7f964..3849ef3 100644 --- a/reddinator/src/main/java/au/com/wallaceit/reddinator/ui/SubredditFeedAdapter.java +++ b/reddinator/src/main/java/au/com/wallaceit/reddinator/ui/SubredditFeedAdapter.java @@ -20,13 +20,14 @@ * Created by michael on 3/10/16. */ +import android.app.Activity; import android.appwidget.AppWidgetManager; import android.content.Context; import android.content.Intent; import android.graphics.Bitmap; -import android.graphics.BitmapFactory; import android.graphics.Color; import android.os.Bundle; +import android.util.DisplayMetrics; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; @@ -76,6 +77,7 @@ public class SubredditFeedAdapter extends BaseAdapter implements VoteTask.Callba private boolean bigThumbs = false; private boolean hideInf = false; private boolean showItemSubreddit = false; + private int maxDisplayPixels = 2048; public interface ActivityInterface { void loadMore(); @@ -101,6 +103,7 @@ public SubredditFeedAdapter(Context context, ActivityInterface feedInterface, Re // load preferences loadTheme(); loadFeedPrefs(); + setMaxDisplayPixels((Activity) context); } public void setFeed(JSONArray data, boolean canLoadMore, boolean hasMultipleSubs){ @@ -232,6 +235,12 @@ public void loadFeedPrefs() { hideInf = global.mSharedPreferences.getBoolean("hideinf-app", false); } + private void setMaxDisplayPixels(Activity activity) { + DisplayMetrics displayMetrics = new DisplayMetrics(); + activity.getWindowManager().getDefaultDisplay().getMetrics(displayMetrics); + maxDisplayPixels = displayMetrics.heightPixels; + } + @Override public int getCount() { return data.length()>0 ? (data.length() + 1) : 0; // plus 1 advertises the "load more" item to the listview without having to add it to the data source @@ -428,7 +437,9 @@ public void onClick(View view) { // check if the image is in cache String fileurl = context.getCacheDir() + Reddinator.IMAGE_CACHE_DIR + id + (imageLoadFlag == 2 ? "-preview" : "") + ".png"; if (new File(fileurl).exists()) { - Bitmap bitmap = BitmapFactory.decodeFile(fileurl); + + // Load bitmap, making sure to limit dimensions to avoid images that are too large. + Bitmap bitmap = Utilities.decodeSampledBitmapFromFile(fileurl, maxDisplayPixels, maxDisplayPixels); if (bitmap == null) { imageView.setVisibility(View.GONE); } else {