try improving the image loading performance on weaker devices
This commit is contained in:
parent
f2b41a3758
commit
a66596f160
3 changed files with 27 additions and 9 deletions
|
@ -251,7 +251,6 @@ class PhotoFragment : ViewPagerFragment() {
|
||||||
|
|
||||||
override fun onConfigurationChanged(newConfig: Configuration) {
|
override fun onConfigurationChanged(newConfig: Configuration) {
|
||||||
super.onConfigurationChanged(newConfig)
|
super.onConfigurationChanged(newConfig)
|
||||||
|
|
||||||
if (!mWasInit) {
|
if (!mWasInit) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
@ -272,6 +271,7 @@ class PhotoFragment : ViewPagerFragment() {
|
||||||
loadImage()
|
loadImage()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
measureScreen()
|
||||||
initExtendedDetails()
|
initExtendedDetails()
|
||||||
updateInstantSwitchWidths()
|
updateInstantSwitchWidths()
|
||||||
}
|
}
|
||||||
|
@ -461,13 +461,14 @@ class PhotoFragment : ViewPagerFragment() {
|
||||||
mIsSubsamplingVisible = true
|
mIsSubsamplingVisible = true
|
||||||
val config = context!!.config
|
val config = context!!.config
|
||||||
val showHighestQuality = config.showHighestQuality
|
val showHighestQuality = config.showHighestQuality
|
||||||
|
val minTileDpi = if (showHighestQuality) -1 else getMinTileDpi()
|
||||||
|
|
||||||
val bitmapDecoder = object : DecoderFactory<ImageDecoder> {
|
val bitmapDecoder = object : DecoderFactory<ImageDecoder> {
|
||||||
override fun make() = PicassoDecoder(mMedium.path, Picasso.get(), rotation)
|
override fun make() = PicassoDecoder(mMedium.path, Picasso.get(), rotation)
|
||||||
}
|
}
|
||||||
|
|
||||||
val regionDecoder = object : DecoderFactory<ImageRegionDecoder> {
|
val regionDecoder = object : DecoderFactory<ImageRegionDecoder> {
|
||||||
override fun make() = PicassoRegionDecoder(showHighestQuality)
|
override fun make() = PicassoRegionDecoder(showHighestQuality, mScreenWidth, mScreenHeight, minTileDpi)
|
||||||
}
|
}
|
||||||
|
|
||||||
var newOrientation = (rotation + mCurrentRotationDegrees) % 360
|
var newOrientation = (rotation + mCurrentRotationDegrees) % 360
|
||||||
|
@ -477,7 +478,7 @@ class PhotoFragment : ViewPagerFragment() {
|
||||||
|
|
||||||
mView.subsampling_view.apply {
|
mView.subsampling_view.apply {
|
||||||
setMaxTileSize(if (showHighestQuality) Integer.MAX_VALUE else 4096)
|
setMaxTileSize(if (showHighestQuality) Integer.MAX_VALUE else 4096)
|
||||||
setMinimumTileDpi(if (showHighestQuality) -1 else getMinTileDpi())
|
setMinimumTileDpi(minTileDpi)
|
||||||
background = ColorDrawable(Color.TRANSPARENT)
|
background = ColorDrawable(Color.TRANSPARENT)
|
||||||
bitmapDecoderFactory = bitmapDecoder
|
bitmapDecoderFactory = bitmapDecoder
|
||||||
regionDecoderFactory = regionDecoder
|
regionDecoderFactory = regionDecoder
|
||||||
|
@ -487,6 +488,7 @@ class PhotoFragment : ViewPagerFragment() {
|
||||||
isOneToOneZoomEnabled = config.allowOneToOneZoom
|
isOneToOneZoomEnabled = config.allowOneToOneZoom
|
||||||
orientation = newOrientation
|
orientation = newOrientation
|
||||||
setImage(mMedium.path)
|
setImage(mMedium.path)
|
||||||
|
|
||||||
onImageEventListener = object : SubsamplingScaleImageView.OnImageEventListener {
|
onImageEventListener = object : SubsamplingScaleImageView.OnImageEventListener {
|
||||||
override fun onReady() {
|
override fun onReady() {
|
||||||
background = ColorDrawable(if (config.blackBackground) Color.BLACK else config.backgroundColor)
|
background = ColorDrawable(if (config.blackBackground) Color.BLACK else config.backgroundColor)
|
||||||
|
@ -520,10 +522,10 @@ class PhotoFragment : ViewPagerFragment() {
|
||||||
val averageDpi = (metrics.xdpi + metrics.ydpi) / 2
|
val averageDpi = (metrics.xdpi + metrics.ydpi) / 2
|
||||||
val device = "${Build.BRAND} ${Build.MODEL}".toLowerCase()
|
val device = "${Build.BRAND} ${Build.MODEL}".toLowerCase()
|
||||||
return when {
|
return when {
|
||||||
WEIRD_DEVICES.contains(device) -> 240
|
WEIRD_DEVICES.contains(device) -> WEIRD_TILE_DPI
|
||||||
averageDpi > 400 -> 280
|
averageDpi > 400 -> HIGH_TILE_DPI
|
||||||
averageDpi > 300 -> 220
|
averageDpi > 300 -> NORMAL_TILE_DPI
|
||||||
else -> 160
|
else -> LOW_TILE_DPI
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -208,3 +208,9 @@ const val MAX_VIDEO_ZOOM_SCALE = 5f
|
||||||
const val ZOOM_MODE_NONE = 0
|
const val ZOOM_MODE_NONE = 0
|
||||||
const val ZOOM_MODE_DRAG = 1
|
const val ZOOM_MODE_DRAG = 1
|
||||||
const val ZOOM_MODE_ZOOM = 2
|
const val ZOOM_MODE_ZOOM = 2
|
||||||
|
|
||||||
|
// constants related to image quality
|
||||||
|
const val LOW_TILE_DPI = 160
|
||||||
|
const val NORMAL_TILE_DPI = 220
|
||||||
|
const val WEIRD_TILE_DPI = 240
|
||||||
|
const val HIGH_TILE_DPI = 280
|
||||||
|
|
|
@ -5,7 +5,7 @@ import android.graphics.*
|
||||||
import android.net.Uri
|
import android.net.Uri
|
||||||
import com.davemorrissey.labs.subscaleview.ImageRegionDecoder
|
import com.davemorrissey.labs.subscaleview.ImageRegionDecoder
|
||||||
|
|
||||||
class PicassoRegionDecoder(val showHighestQuality: Boolean) : ImageRegionDecoder {
|
class PicassoRegionDecoder(val showHighestQuality: Boolean, val screenWidth: Int, val screenHeight: Int, val minTileDpi: Int) : ImageRegionDecoder {
|
||||||
private var decoder: BitmapRegionDecoder? = null
|
private var decoder: BitmapRegionDecoder? = null
|
||||||
private val decoderLock = Any()
|
private val decoderLock = Any()
|
||||||
|
|
||||||
|
@ -18,10 +18,20 @@ class PicassoRegionDecoder(val showHighestQuality: Boolean) : ImageRegionDecoder
|
||||||
|
|
||||||
override fun decodeRegion(rect: Rect, sampleSize: Int): Bitmap {
|
override fun decodeRegion(rect: Rect, sampleSize: Int): Bitmap {
|
||||||
synchronized(decoderLock) {
|
synchronized(decoderLock) {
|
||||||
|
var newSampleSize = sampleSize
|
||||||
|
if (!showHighestQuality && minTileDpi == LOW_TILE_DPI) {
|
||||||
|
if ((rect.width() > rect.height() && screenWidth > screenHeight) || (rect.height() > rect.width() && screenHeight > screenWidth)) {
|
||||||
|
if ((rect.width() / sampleSize > screenWidth || rect.height() / sampleSize > screenHeight)) {
|
||||||
|
newSampleSize *= 2
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
val options = BitmapFactory.Options()
|
val options = BitmapFactory.Options()
|
||||||
options.inSampleSize = sampleSize
|
options.inSampleSize = newSampleSize
|
||||||
options.inPreferredConfig = if (showHighestQuality) Bitmap.Config.ARGB_8888 else Bitmap.Config.RGB_565
|
options.inPreferredConfig = if (showHighestQuality) Bitmap.Config.ARGB_8888 else Bitmap.Config.RGB_565
|
||||||
val bitmap = decoder!!.decodeRegion(rect, options)
|
val bitmap = decoder!!.decodeRegion(rect, options)
|
||||||
|
|
||||||
return bitmap ?: throw RuntimeException("Region decoder returned null bitmap - image format may not be supported")
|
return bitmap ?: throw RuntimeException("Region decoder returned null bitmap - image format may not be supported")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue