From d57bd836a25312a5cb8014b2fea0d4447f500d5b Mon Sep 17 00:00:00 2001 From: tateisu Date: Tue, 30 Jan 2018 21:28:01 +0900 Subject: [PATCH] =?UTF-8?q?bitmap=E3=81=AErecycle=E6=BC=8F=E3=82=8C?= =?UTF-8?q?=E3=82=92=E4=BF=AE=E6=AD=A3?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../jp/juggler/apng/ApngDecoderCallback.kt | 2 +- .../main/java/jp/juggler/apng/ApngFrames.kt | 63 ++++++++++--------- 2 files changed, 33 insertions(+), 32 deletions(-) diff --git a/apng/src/main/java/jp/juggler/apng/ApngDecoderCallback.kt b/apng/src/main/java/jp/juggler/apng/ApngDecoderCallback.kt index ad30e0ba..ab1571d7 100644 --- a/apng/src/main/java/jp/juggler/apng/ApngDecoderCallback.kt +++ b/apng/src/main/java/jp/juggler/apng/ApngDecoderCallback.kt @@ -26,6 +26,6 @@ interface ApngDecoderCallback { // called when APNG Frame Control is detected and its bitmap was rendered. // its bitmap may same to default image for first frame. // ( in this case, both of onDefaultImage and onAnimationFrame are called for same bitmap) - fun onAnimationFrame(apng : Apng, frameControl : ApngFrameControl, bitmap : ApngBitmap) + fun onAnimationFrame(apng : Apng, frameControl : ApngFrameControl, frameBitmap : ApngBitmap) } diff --git a/apng_android/src/main/java/jp/juggler/apng/ApngFrames.kt b/apng_android/src/main/java/jp/juggler/apng/ApngFrames.kt index 0a3fe93f..9986437a 100644 --- a/apng_android/src/main/java/jp/juggler/apng/ApngFrames.kt +++ b/apng_android/src/main/java/jp/juggler/apng/ApngFrames.kt @@ -36,8 +36,7 @@ class ApngFrames private constructor( } // WARNING: ownership of "src" will be moved or recycled. - private fun scaleBitmap(src : Bitmap?, size_max : Int) : Bitmap? { - if(src == null) return null + private fun scaleBitmap(src : Bitmap, size_max : Int) : Bitmap { val wSrc = src.width val hSrc = src.height @@ -71,7 +70,7 @@ class ApngFrames private constructor( return b2 } - private fun toBitmap(src : ApngBitmap) : Bitmap { + private fun toAndroidBitmap(src : ApngBitmap) : Bitmap { return Bitmap.createBitmap( src.colors, // int[] 配列 0, // offset @@ -82,12 +81,8 @@ class ApngFrames private constructor( ) } - private fun toBitmap(src : ApngBitmap, size_max : Int) : Bitmap? { - return scaleBitmap( - toBitmap( - src - ), size_max - ) + private fun toAndroidBitmap(src : ApngBitmap, size_max : Int) : Bitmap { + return scaleBitmap( toAndroidBitmap( src ), size_max ) } @Suppress("unused") @@ -112,11 +107,11 @@ class ApngFrames private constructor( private var header : ApngImageHeader? = null private var animationControl : ApngAnimationControl? = null - val width : Int - get() = Math.min( pixelSizeMax, header?.width ?: 1) + var width : Int =1 + private set - val height : Int - get() = Math.min( pixelSizeMax, header?.height ?: 1) + var height : Int = 1 + private set @Suppress("MemberVisibilityCanBePrivate") val numFrames : Int @@ -264,6 +259,9 @@ class ApngFrames private constructor( override fun onHeader(apng : Apng, header : ApngImageHeader) { this.header = header + + + } override fun onAnimationInfo( @@ -281,23 +279,24 @@ class ApngFrames private constructor( } override fun onDefaultImage(apng : Apng, bitmap : ApngBitmap) { + val androidBitmap = toAndroidBitmap(bitmap, pixelSizeMax) + this.width = androidBitmap.width + this.height = androidBitmap.height + defaultImage?.recycle() - defaultImage = toBitmap(bitmap, pixelSizeMax) + defaultImage = androidBitmap } override fun onAnimationFrame( apng : Apng, frameControl : ApngFrameControl, - bitmap : ApngBitmap + frameBitmap : ApngBitmap ) { val frames = this.frames ?: return val canvasBitmap = this.canvasBitmap ?: return - // APNGのフレーム画像をAndroidの形式に変換する。この段階ではリサイズしない - val bitmapNative = toBitmap(bitmap) - val previous : Bitmap? = if(frameControl.disposeOp == DisposeOp.Previous) { - // Capture the current bitmap region IF it needs to be reverted after rendering + // Capture the current frameBitmap region IF it needs to be reverted after rendering Bitmap.createBitmap( canvasBitmap, frameControl.xOffset, @@ -315,30 +314,32 @@ class ApngFrames private constructor( null // (for blend, leave paint null) } + + // APNGのフレーム画像をAndroidの形式に変換する。この段階ではリサイズしない + val frameBitmapAndroid = toAndroidBitmap(frameBitmap) + // Draw the new frame into place canvas.drawBitmap( - bitmapNative, + frameBitmapAndroid, frameControl.xOffset.toFloat(), frameControl.yOffset.toFloat(), paint ) - // Extract a drawable from the canvas. Have to copy the current bitmap. + frameBitmapAndroid.recycle() + + // Extract a drawable from the canvas. Have to copy the current frameBitmap. // Store the drawable in the sequence of frames val timeStart = timeTotal val timeWidth = Math.max(1L, frameControl.delayMilliseconds) timeTotal += timeWidth - val scaledBitmap = - scaleBitmap( - canvasBitmap.copy( - Bitmap.Config.ARGB_8888, - false - ), pixelSizeMax - ) - if(scaledBitmap != null) { - frames.add(Frame(scaledBitmap, timeStart, timeWidth)) - } + val scaledBitmap = scaleBitmap( + canvasBitmap.copy( Bitmap.Config.ARGB_8888, false ), + pixelSizeMax + ) + + frames.add(Frame(scaledBitmap, timeStart, timeWidth)) // Now "dispose" of the frame in preparation for the next. // https://wiki.mozilla.org/APNG_Specification#.60fcTL.60:_The_Frame_Control_Chunk