package com.jimmydaddy.imagemarker.base import android.graphics.Bitmap import android.graphics.BitmapFactory import android.graphics.Matrix import android.media.ExifInterface import android.util.Log import com.facebook.react.bridge.Dynamic import com.facebook.react.bridge.ReadableType import java.io.IOException import java.io.InputStream import java.net.HttpURLConnection import java.net.URL /** * Created by jimmydaddy on 2018/4/8. */ class Utils { companion object { var TAG = "[ImageMarker]" @JvmStatic fun getBlankBitmap(width: Int, height: Int): Bitmap? { var icon: Bitmap? = null try { icon = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888) } catch (e: OutOfMemoryError) { print(e.message) while (icon == null) { System.gc() System.runFinalization() icon = Bitmap.createBitmap(width, height, Bitmap.Config.RGB_565) } } return icon } private fun readDegree(path: String?): Int { var degree = 0 try { val exifInterface = ExifInterface(path!!) val orientation = exifInterface.getAttributeInt( ExifInterface.TAG_ORIENTATION, ExifInterface.ORIENTATION_NORMAL ) when (orientation) { ExifInterface.ORIENTATION_ROTATE_90 -> degree = 90 ExifInterface.ORIENTATION_ROTATE_180 -> degree = 180 ExifInterface.ORIENTATION_ROTATE_270 -> degree = 270 } } catch (e: IOException) { e.printStackTrace() } return degree } @JvmStatic fun scaleBitmap(bitmap: Bitmap, scale: Float): Bitmap? { val w = bitmap.width val h = bitmap.height val mtx = Matrix() if (scale != 1f && scale >= 0) { mtx.postScale(scale, scale) } var scaledBitmap: Bitmap? = null try { scaledBitmap = Bitmap.createBitmap(bitmap, 0, 0, w, h, mtx, true) } catch (e: OutOfMemoryError) { print(e.message) while (scaledBitmap == null) { System.gc() System.runFinalization() scaledBitmap = Bitmap.createBitmap(bitmap, 0, 0, w, h, mtx, true) } } return scaledBitmap } fun transRGBColor(color: String?): String { val colorStr = color!!.substring(1) if (colorStr.length == 3) { var fullColor = "" for (i in colorStr.indices) { val temp = colorStr.substring(i, i + 1) fullColor += temp + temp } return "#$fullColor" } if (colorStr.length == 4) { val alpha = colorStr.substring(3, 4) val hexColor = colorStr.substring(0, 3) var fullColor = alpha + alpha for (i in hexColor.indices) { val temp = colorStr.substring(i, i + 1) fullColor += temp + temp } return "#$fullColor" } return if (colorStr.length == 8) { val alpha = colorStr.substring(6, 8) val hexColor = colorStr.substring(0, 6) "#$alpha$hexColor" } else { color } } @JvmStatic fun getStringSafe(key: String?, map: Map): String? { val obj = map[key] return obj?.toString() } /** * read stream from remote * * @param url * @return */ fun getStreamFromInternet(url: String): InputStream? { var connection: HttpURLConnection? = null try { val mUrl = URL(url) connection = mUrl.openConnection() as HttpURLConnection connection.requestMethod = "GET" // 10 秒超时时间 connection.connectTimeout = 10000 connection.readTimeout = 10000 connection.connect() val responseCode = connection.responseCode if (responseCode == 200) { return connection.inputStream } else { Log.d(TAG, "getStreamFromInternet: read stream from remote: $url failed") } } catch (e: Exception) { e.printStackTrace() } finally { connection?.disconnect() } return null } fun checkSpreadValue(str: String?, maxLength: Int = 1): Boolean { if (str == null) return false val pattern = """^((\d+|\d+%)\s?){1,$maxLength}$""".toRegex() return pattern.containsMatchIn(str) } fun parseSpreadValue(v: String?, relativeTo: Float): Float { if (v == null) return 0f return if (v.endsWith("%")) { val percent = v.dropLast(1).toFloatOrNull()?.div(100) ?: 0f relativeTo * percent } else { v.toFloatOrNull() ?: 0f } } fun handleDynamicToString(d: Dynamic?): String { return if (d == null) { "0" } else { when (d.type) { ReadableType.String -> d.asString() ?: "0" ReadableType.Number -> d.asDouble().toString() else -> "0" } } } } /** * 获取最大内存使用 * * @return */ val maxMemory: Int get() = Runtime.getRuntime().maxMemory().toInt() / 1024 fun scaleBitmap(path: String?, scale: Float): Bitmap? { val degree = readDegree(path) val options = BitmapFactory.Options() var prePhoto: Bitmap? = null options.inSampleSize = scale.toInt() try { prePhoto = BitmapFactory.decodeFile(path, options) } catch (e: OutOfMemoryError) { print(e.message) while (prePhoto == null) { System.gc() System.runFinalization() prePhoto = BitmapFactory.decodeFile(path, options) } } // if (prePhoto == null) return null val w = options.outWidth val h = options.outHeight val mtx = Matrix() mtx.postRotate(degree.toFloat()) if (scale != 1f && scale >= 0) { mtx.postScale(scale, scale) } var scaledBitmap: Bitmap? = null try { scaledBitmap = Bitmap.createBitmap(prePhoto, 0, 0, w, h, mtx, true) } catch (e: OutOfMemoryError) { print(e.message) while (scaledBitmap == null) { System.gc() System.runFinalization() scaledBitmap = Bitmap.createBitmap(prePhoto, 0, 0, w, h, mtx, true) } } return scaledBitmap } }