From 30da9477516d104bacf8ded7acea0a22436512f0 Mon Sep 17 00:00:00 2001 From: Jieyi Date: Thu, 28 Feb 2019 18:56:07 +0900 Subject: [PATCH] Feature: added more utils. --- kotlinknifer/build.gradle | 5 +- .../com/devrapid/kotlinknifer/Animation.kt | 113 ++++++++++++++++++ .../java/com/devrapid/kotlinknifer/Bitmap.kt | 64 ++++++++-- .../java/com/devrapid/kotlinknifer/Bundle.kt | 24 ++++ .../com/devrapid/kotlinknifer/Collection.kt | 4 - .../java/com/devrapid/kotlinknifer/Color.kt | 43 +++---- .../java/com/devrapid/kotlinknifer/Context.kt | 10 ++ .../com/devrapid/kotlinknifer/Delegate.kt | 14 +-- .../java/com/devrapid/kotlinknifer/Display.kt | 6 +- .../com/devrapid/kotlinknifer/Drawable.kt | 47 ++------ .../com/devrapid/kotlinknifer/Fragment.kt | 4 - .../java/com/devrapid/kotlinknifer/Glide.kt | 49 -------- .../com/devrapid/kotlinknifer/Keyboard.kt | 4 - .../com/devrapid/kotlinknifer/Listener.kt | 19 ++- .../java/com/devrapid/kotlinknifer/Logs.kt | 10 -- .../java/com/devrapid/kotlinknifer/Network.kt | 26 ++++ .../com/devrapid/kotlinknifer/Resolution.kt | 4 - .../java/com/devrapid/kotlinknifer/Screen.kt | 6 +- .../com/devrapid/kotlinknifer/Spannable.kt | 27 +++++ .../java/com/devrapid/kotlinknifer/Toast.kt | 16 +++ .../java/com/devrapid/kotlinknifer/View.kt | 8 +- .../com/devrapid/kotlinknifer/ViewStub.kt | 28 +++++ .../kotlinknifer/recyclerview/Extensions.kt | 13 ++ .../WrapContentLinearLayoutManager.kt | 6 - .../com/devrapid/kotlinshaver/ArrayList.kt | 10 +- .../java/com/devrapid/kotlinshaver/Casting.kt | 1 + .../com/devrapid/kotlinshaver/Coroutine.kt | 8 +- .../java/com/devrapid/kotlinshaver/Field.kt | 2 - .../com/devrapid/kotlinshaver/Instance.kt | 7 +- .../java/com/devrapid/kotlinshaver/Int.kt | 2 - .../java/com/devrapid/kotlinshaver/Kits.kt | 5 - .../java/com/devrapid/kotlinshaver/String.kt | 8 +- .../java/com/devrapid/kotlinshaver/Thread.kt | 8 +- .../java/com/devrapid/kotlinshaver/Time.kt | 25 ++-- .../com/devrapid/kotlinshaver/TypeAliases.kt | 8 ++ .../kotlinshaver/{ => rxjava2}/Completable.kt | 8 +- .../kotlinshaver/{ => rxjava2}/Observable.kt | 7 +- .../kotlinshaver/{ => rxjava2}/Observer.kt | 10 +- .../kotlinshaver/{ => rxjava2}/Single.kt | 8 +- 39 files changed, 393 insertions(+), 274 deletions(-) create mode 100644 kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Animation.kt create mode 100644 kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Bundle.kt create mode 100644 kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Context.kt create mode 100644 kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Network.kt create mode 100644 kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Spannable.kt create mode 100644 kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Toast.kt create mode 100644 kotlinknifer/src/main/java/com/devrapid/kotlinknifer/ViewStub.kt create mode 100644 kotlinknifer/src/main/java/com/devrapid/kotlinknifer/recyclerview/Extensions.kt create mode 100644 kotlinshaver/src/main/java/com/devrapid/kotlinshaver/TypeAliases.kt rename kotlinshaver/src/main/java/com/devrapid/kotlinshaver/{ => rxjava2}/Completable.kt (89%) rename kotlinshaver/src/main/java/com/devrapid/kotlinshaver/{ => rxjava2}/Observable.kt (95%) rename kotlinshaver/src/main/java/com/devrapid/kotlinshaver/{ => rxjava2}/Observer.kt (90%) rename kotlinshaver/src/main/java/com/devrapid/kotlinshaver/{ => rxjava2}/Single.kt (90%) diff --git a/kotlinknifer/build.gradle b/kotlinknifer/build.gradle index 07befb5..0ce1017 100644 --- a/kotlinknifer/build.gradle +++ b/kotlinknifer/build.gradle @@ -26,14 +26,15 @@ dependencies { implementation "org.jetbrains.kotlin:kotlin-stdlib:$kotlin_version" // 'compile' can also import to the new project with this. compile "com.google.code.gson:gson:2.8.5" - compile "com.github.bumptech.glide:glide:4.8.0" + compile "com.github.bumptech.glide:glide:4.9.0" // 'implementation' can't import to the new project. implementation "org.jetbrains.kotlinx:kotlinx-coroutines-core:$kotlin_coroutine_version" implementation "org.jetbrains.kotlinx:kotlinx-coroutines-core-common:$kotlin_coroutine_version" implementation "org.jetbrains.kotlinx:kotlinx-coroutines-android:$kotlin_coroutine_version" implementation "org.jetbrains.anko:anko-commons:0.10.8" implementation "androidx.appcompat:appcompat:1.0.2" - implementation "androidx.recyclerview:recyclerview:1.1.0-alpha01" + implementation "androidx.core:core-ktx:1.0.1" + implementation "androidx.recyclerview:recyclerview:1.1.0-alpha02" implementation "androidx.palette:palette:1.0.0" compile project(":kotlinshaver") } diff --git a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Animation.kt b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Animation.kt new file mode 100644 index 0000000..2aff89b --- /dev/null +++ b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Animation.kt @@ -0,0 +1,113 @@ +package com.devrapid.kotlinknifer + +import android.animation.Animator +import android.animation.AnimatorListenerAdapter +import android.animation.ArgbEvaluator +import android.animation.ValueAnimator +import android.os.Build +import android.os.Parcel +import android.os.Parcelable +import android.view.View +import android.view.ViewAnimationUtils +import androidx.interpolator.view.animation.FastOutSlowInInterpolator +import kotlin.math.pow + +fun View.registerCircularRevealAnimation( + revealSettings: RevealAnimationSetting, + startColor: Int, + endColor: Int +) { + val duration = 1000L + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { + addOnLayoutChangeListener(object : View.OnLayoutChangeListener { + override fun onLayoutChange( + v: View, + left: Int, + top: Int, + right: Int, + bottom: Int, + oldLeft: Int, + oldTop: Int, + oldRight: Int, + oldBottom: Int + ) { + v.removeOnLayoutChangeListener(this) + val (cx, cy, width, height) = revealSettings + + // Simply use the diagonal of the view. + val radius = Math.sqrt((width.toDouble().pow(2) + height.toDouble().pow(2))).toFloat() + ViewAnimationUtils.createCircularReveal(v, cx, cy, 0f, radius).apply { + this.duration = duration + interpolator = FastOutSlowInInterpolator() + }.start() + } + }) + startColorAnimation(startColor, endColor, duration) + } +} + +fun View.startCircularExitAnimation( + revealSettings: RevealAnimationSetting, + startColor: Int, + endColor: Int, + listener: () -> Unit +) { + val duration = 1000L + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { + val (cx, cy, width, height) = revealSettings + + // Simply use the diagonal of the view. + val radius = Math.sqrt((width.toDouble().pow(2) + height.toDouble().pow(2))).toFloat() + ViewAnimationUtils.createCircularReveal(this, cx, cy, radius, 0f).apply { + this.duration = duration + interpolator = FastOutSlowInInterpolator() + addListener(object : AnimatorListenerAdapter() { + override fun onAnimationEnd(animation: Animator) { + gone() + listener() + } + }) + }.start() + startColorAnimation(startColor, endColor, duration) + } + else { + listener() + } +} + +fun View.startColorAnimation( + startColor: Int, + endColor: Int, + duration: Long +) { + ValueAnimator().apply { + this.duration = duration + setIntValues(startColor, endColor) + setEvaluator(ArgbEvaluator()) + addUpdateListener { setBackgroundColor(it.animatedValue as Int) } + }.start() +} + +data class RevealAnimationSetting( + var centerX: Int, + var centerY: Int, + var width: Int, + var height: Int +) : Parcelable { + companion object CREATOR : Parcelable.Creator { + override fun createFromParcel(parcel: Parcel) = RevealAnimationSetting(parcel) + + override fun newArray(size: Int) = arrayOfNulls(size) + } + + constructor(parcel: Parcel) : this(parcel.readInt(), parcel.readInt(), parcel.readInt(), parcel.readInt()) + + override fun writeToParcel(parcel: Parcel, flags: Int) { + parcel.writeInt(centerX) + parcel.writeInt(centerY) + parcel.writeInt(width) + parcel.writeInt(height) + } + + override fun describeContents(): Int = 0 +} diff --git a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Bitmap.kt b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Bitmap.kt index 17e5f22..ac8cc4b 100644 --- a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Bitmap.kt +++ b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Bitmap.kt @@ -1,15 +1,25 @@ package com.devrapid.kotlinknifer +import android.content.Context import android.content.res.Resources import android.graphics.Bitmap import android.graphics.BitmapFactory import android.graphics.BitmapRegionDecoder +import android.graphics.BitmapShader import android.graphics.Canvas +import android.graphics.ComposeShader +import android.graphics.Paint +import android.graphics.PorterDuff import android.graphics.Rect +import android.graphics.Shader import android.graphics.drawable.BitmapDrawable -import android.graphics.drawable.Drawable +import android.renderscript.Allocation +import android.renderscript.Element +import android.renderscript.RenderScript +import android.renderscript.ScriptIntrinsicBlur import android.util.Size import androidx.annotation.DrawableRes +import androidx.palette.graphics.Palette import java.io.ByteArrayOutputStream /** @@ -86,19 +96,11 @@ fun Resources.createRegionBitmap( decoder.decodeRegion(rect, opts) } -fun Drawable.toBitmap(): Bitmap { - if (this is BitmapDrawable) return bitmap +inline fun Bitmap.toDrawable(context: Context) = BitmapDrawable(context.resources, this) - val width = if (bounds.isEmpty) intrinsicWidth else bounds.width() - val height = if (bounds.isEmpty) intrinsicHeight else bounds.height() +inline fun Bitmap.palette() = Palette.from(this) - return Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888).also { - Canvas(it).let { - setBounds(0, 0, it.width, it.height) - draw(it) - } - } -} +inline fun Bitmap.palette(maxColorCount: Int) = Palette.from(this).maximumColorCount(maxColorCount).generate() fun Bitmap.toBytes(format: Bitmap.CompressFormat = Bitmap.CompressFormat.PNG, quality: Int = 100) { val stream = ByteArrayOutputStream() @@ -120,6 +122,44 @@ fun Bitmap?.safeRecycle() { recycle() } +fun Bitmap.decorateGradientMask(shaderDst: Shader): Bitmap { + val res = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888) + val canvas = Canvas(res) + // Create the source shader bitmap. + val shaderSrc = BitmapShader(this, Shader.TileMode.CLAMP, Shader.TileMode.CLAMP) + + val paint = Paint().apply { + shader = ComposeShader(shaderDst, shaderSrc, PorterDuff.Mode.SRC_IN) + } + canvas.drawRect(0f, 0f, width.toFloat(), height.toFloat(), paint) + + return res +} + +fun Context.blurBitmap(image: Bitmap, radius: Float = 25f, scale: Float = 0.4f): Bitmap { + val width = Math.round(image.width * scale) + val height = Math.round(image.height * scale) + // Because of the blurring, we don't have to use original bitmap to blur. It's able to reduce cost. + val scaledBitmap = Bitmap.createScaledBitmap(image, width, height, false) + // Create a image for blurring. + val blurBitmap = Bitmap.createBitmap(scaledBitmap) + val rs = RenderScript.create(this) + // RenderScript doesn't use VM to allocate memory, we have to do it by ourselves. + val tmpIn = Allocation.createFromBitmap(rs, scaledBitmap) + // The created Allocation is empty actually, copyTo() is necessary to fill the date. + val tmpOut = Allocation.createFromBitmap(rs, blurBitmap) + + ScriptIntrinsicBlur.create(rs, Element.U8_4(rs)).apply { + setRadius(radius) + setInput(tmpIn) + forEach(tmpOut) + } + + tmpOut.copyTo(blurBitmap) + + return blurBitmap +} + object ImageUtils { /** * @param originWidth the width of the origin bitmap diff --git a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Bundle.kt b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Bundle.kt new file mode 100644 index 0000000..a564a76 --- /dev/null +++ b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Bundle.kt @@ -0,0 +1,24 @@ +package com.devrapid.kotlinknifer + +import android.app.Activity +import androidx.fragment.app.Fragment + +inline fun Activity.extra(key: String, default: T? = null) = lazy { + val value = intent?.extras?.get(key) + if (value is T) value else default +} + +inline fun Activity.extraNotNull(key: String, default: T? = null) = lazy { + val value = intent?.extras?.get(key) + requireNotNull(if (value is T) value else default) { key } +} + +inline fun Fragment.extra(key: String, default: T? = null) = lazy { + val value = arguments?.get(key) + if (value is T) value else default +} + +inline fun Fragment.extraNotNull(key: String, default: T? = null) = lazy { + val value = arguments?.get(key) + requireNotNull(if (value is T) value else default) { key } +} diff --git a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Collection.kt b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Collection.kt index f01d799..02b9868 100644 --- a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Collection.kt +++ b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Collection.kt @@ -4,10 +4,6 @@ package com.devrapid.kotlinknifer import java.util.Stack -/** - * @author jieyi - * @since 2018/01/12 - */ inline fun Stack.safePop() = lastOrNull()?.let { pop() } inline fun Stack.safePeek() = lastOrNull()?.let { peek() } diff --git a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Color.kt b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Color.kt index 42c31fa..9c040a9 100644 --- a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Color.kt +++ b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Color.kt @@ -1,5 +1,3 @@ -@file:Suppress("NOTHING_TO_INLINE", "EXTENSION_SHADOWED_BY_MEMBER") - package com.devrapid.kotlinknifer import android.content.Context @@ -8,12 +6,8 @@ import android.view.View import androidx.annotation.ColorInt import androidx.annotation.ColorRes import androidx.core.content.ContextCompat +import androidx.fragment.app.Fragment -/** - * - * @author jieyi - * @since 5/30/17 - */ /** * Add the alpha into the [Color] from resource id. * @@ -23,39 +17,29 @@ import androidx.core.content.ContextCompat * @return transparent RGB integer resColor */ @ColorInt -inline fun Context.getResColorWithAlpha(@ColorRes resColor: Int, ratio: Float): Int = - this.getColorWithAlpha(this.getResColor(resColor), ratio) +inline fun Context.getColorOfAlpha(@ColorRes resColor: Int, ratio: Float) = + ContextCompat.getColor(this, resColor).ofAlpha(ratio) @ColorInt -inline fun View.getResColorWithAlpha(@ColorRes resColor: Int, ratio: Float): Int = - this.context.getResColorWithAlpha(resColor, ratio) +inline fun Fragment.getColorOfAlpha(@ColorRes resColor: Int, ratio: Float) = getColor(resColor).ofAlpha(ratio) + +@ColorInt +inline fun View.getColorOfAlpha(@ColorRes resColor: Int, ratio: Float) = getColor(resColor).ofAlpha(ratio) /** * Add the alpha into the Color. * - * @param color opaque RGB integer color for ex: -11517920 * @param ratio ratio of transparency for ex: 0.5f * * @return transparent RGB integer resColor */ @ColorInt -inline fun Context.getColorWithAlpha(@ColorInt color: Int, ratio: Float): Int { - val a: Int = Math.round(Color.alpha(color) * ratio) +inline fun Int.ofAlpha(ratio: Float): Int { + val alpha = Math.round(Color.alpha(this) * ratio) - return Color.argb(a, Color.red(color), Color.green(color), Color.blue(color)) + return Color.argb(alpha, Color.red(this), Color.green(this), Color.blue(this)) } -@ColorInt -inline fun View.getColorWithAlpha(@ColorInt color: Int, ratio: Float): Int = - this.context.getColorWithAlpha(color, ratio) - -@ColorInt -inline fun Context.getColorInt(@ColorInt color: Int) = - Color.rgb(Color.red(color), Color.green(color), Color.blue(color)) - -@ColorInt -inline fun View.getColorInt(@ColorInt color: Int) = context.getColorInt(color) - /** * Get the [Color] from resource id. * @@ -64,7 +48,7 @@ inline fun View.getColorInt(@ColorInt color: Int) = context.getColorInt(color) * @return transparent RGB integer resColor */ @ColorInt -inline fun Context.getResColor(@ColorRes resColor: Int): Int = ContextCompat.getColor(this, resColor) +inline fun Fragment.getColor(@ColorRes resColor: Int) = ContextCompat.getColor(requireContext(), resColor) /** * Get the [Color] from resource id. @@ -74,4 +58,7 @@ inline fun Context.getResColor(@ColorRes resColor: Int): Int = ContextCompat.get * @return transparent RGB integer resColor */ @ColorInt -inline fun View.getResColor(@ColorRes resColor: Int): Int = ContextCompat.getColor(this.context, resColor) +inline fun View.getColor(@ColorRes resColor: Int) = ContextCompat.getColor(context, resColor) + +@ColorInt +inline fun generateColorInt(@ColorInt color: Int) = Color.rgb(Color.red(color), Color.green(color), Color.blue(color)) diff --git a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Context.kt b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Context.kt new file mode 100644 index 0000000..a68ba2b --- /dev/null +++ b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Context.kt @@ -0,0 +1,10 @@ +package com.devrapid.kotlinknifer + +import android.app.ActivityManager +import android.content.Context +import androidx.appcompat.app.AppCompatActivity + +fun Context.closeCurrentTask(activity: AppCompatActivity) = + (getSystemService(Context.ACTIVITY_SERVICE) as ActivityManager).appTasks + .find { it.taskInfo.id == activity.taskId } + ?.finishAndRemoveTask() diff --git a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Delegate.kt b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Delegate.kt index 7342c6e..cb29022 100644 --- a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Delegate.kt +++ b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Delegate.kt @@ -10,12 +10,6 @@ import kotlin.properties.Delegates import kotlin.properties.ReadWriteProperty import kotlin.reflect.KProperty -/** - * Delegate methods. - * - * @author jieyi - * @since 6/12/17 - */ /** * Wrap the [SoftReference] by kotlin delegate. Don't have to use [get]/[set] method * for accessing or assigning a variable each of times. @@ -125,10 +119,8 @@ class SharedPrefs(var defaultValue: T, val objectType: Class? = null, var is Long -> prefs.getLong(name, defaultValue as Long) as T is String -> prefs.getString(name, defaultValue as String) as T is Set<*> -> prefs.getStringSet(name, defaultValue as Set) as T - // Using json format to deserialize a string to an object. - else -> this.gson.fromJson(prefs.getString(name, - null) ?: throw KotlinNullPointerException("There is no kind of $name was stored in the shared preferences."), - objectType) + // Using json format to deserialize a string to an object. + else -> prefs.getString(name, null)?.let { this.gson.fromJson(it, objectType) } ?: defaultValue } } @@ -143,7 +135,7 @@ class SharedPrefs(var defaultValue: T, val objectType: Class? = null, var is Long -> it.putLong(name, value as Long) is String -> it.putString(name, value as String) is Set<*> -> it.putStringSet(name, value as Set) - // Using json format to serialize an object to a string. + // Using json format to serialize an object to a string. else -> it.putString(name, this.gson.toJson(value)) } this.onChange?.invoke() diff --git a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Display.kt b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Display.kt index b45f9b7..9241bc4 100644 --- a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Display.kt +++ b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Display.kt @@ -6,10 +6,6 @@ import android.content.Context import android.util.DisplayMetrics import android.view.WindowManager -/** - * @author Jieyi Wu - * @since 2018/03/19 - */ inline fun Context.getDisplayMetrics() = DisplayMetrics().also { (getSystemService(Context.WINDOW_SERVICE) as WindowManager).defaultDisplay.getMetrics(it) -} \ No newline at end of file +} diff --git a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Drawable.kt b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Drawable.kt index 5270e1b..97e5e56 100644 --- a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Drawable.kt +++ b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Drawable.kt @@ -1,26 +1,16 @@ -@file:Suppress("NOTHING_TO_INLINE") - package com.devrapid.kotlinknifer import android.content.Context import android.graphics.Bitmap +import android.graphics.Canvas import android.graphics.PorterDuff import android.graphics.PorterDuffColorFilter import android.graphics.Rect import android.graphics.drawable.BitmapDrawable import android.graphics.drawable.Drawable import android.graphics.drawable.ScaleDrawable -import android.renderscript.Allocation -import android.renderscript.Element -import android.renderscript.RenderScript -import android.renderscript.ScriptIntrinsicBlur import androidx.annotation.DrawableRes -import androidx.palette.graphics.Palette -/** - * @author jieyi - * @since 11/20/17 - */ fun Context.scaledDrawable(@DrawableRes drawableId: Int, width: Int, height: Int): Drawable { val drawable = getDrawable(drawableId)?.apply { bounds = Rect(0, 0, width, height) @@ -48,33 +38,16 @@ inline fun Drawable.changeColor(color: Int) = apply { inline fun Int.toDrawable(context: Context) = context.getDrawable(this) -inline fun Bitmap.toDrawable(context: Context) = BitmapDrawable(context.resources, this) - -inline fun Bitmap.palette() = Palette.from(this) - -inline fun Bitmap.palette(maxColorCount: Int) = - Palette.from(this).maximumColorCount(maxColorCount).generate() +fun Drawable.toBitmap(): Bitmap { + if (this is BitmapDrawable) return bitmap -fun Context.blurBitmap(image: Bitmap, radius: Float = 25f, scale: Float = 0.4f): Bitmap { - val width = Math.round(image.width * scale) - val height = Math.round(image.height * scale) - // Because of the blurring, we don't have to use original bitmap to blur. It's able to reduce cost. - val scaledBitmap = Bitmap.createScaledBitmap(image, width, height, false) - // Create a image for blurring. - val blurBitmap = Bitmap.createBitmap(scaledBitmap) - val rs = RenderScript.create(this) - // RenderScript doesn't use VM to allocate memory, we have to do it by ourselves. - val tmpIn = Allocation.createFromBitmap(rs, scaledBitmap) - // The created Allocation is empty actually, copyTo() is necessary to fill the date. - val tmpOut = Allocation.createFromBitmap(rs, blurBitmap) + val width = if (bounds.isEmpty) intrinsicWidth else bounds.width() + val height = if (bounds.isEmpty) intrinsicHeight else bounds.height() - ScriptIntrinsicBlur.create(rs, Element.U8_4(rs)).apply { - setRadius(radius) - setInput(tmpIn) - forEach(tmpOut) + return Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888).also { + Canvas(it).let { + setBounds(0, 0, it.width, it.height) + draw(it) + } } - - tmpOut.copyTo(blurBitmap) - - return blurBitmap } diff --git a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Fragment.kt b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Fragment.kt index 921d7a4..ff73ca5 100644 --- a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Fragment.kt +++ b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Fragment.kt @@ -8,10 +8,6 @@ import androidx.fragment.app.FragmentManager import androidx.fragment.app.FragmentTransaction import java.util.Stack -/** - * @author jieyi - * @since 2/15/17 - */ /** * Adds a [Fragment] to this manager's layout. * Using the [replace] method, we couldn't obtain the fragments. There a way to get it is that diff --git a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Glide.kt b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Glide.kt index 86bc5a4..e7562f7 100644 --- a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Glide.kt +++ b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Glide.kt @@ -5,10 +5,6 @@ import com.bumptech.glide.load.engine.GlideException import com.bumptech.glide.request.RequestListener import com.bumptech.glide.request.target.Target -/** - * @author jieyi - * @since 2018/01/09 - */ fun glideListener(listener: GlideRequestListenerWrapper.() -> Unit): RequestListener { val wrapper = GlideRequestListenerWrapper().apply(listener) @@ -33,21 +29,6 @@ fun glideListener(listener: GlideRequestListenerWrapper.() -> Unit): Requ } class GlideRequestListenerWrapper { - /** - * Called when a load completes successfully, immediately before [Target.onResourceReady]. - * - * @param resource The resource that was loaded for the target. - * @param model The specific model that was used to load the image. - * @param target The target the model was loaded into. - * @param dataSource The [DataSource] the resource was loaded from. - * @param isFirstResource [true] if this is the first resource to in this load to be - * loaded into the target. For example when loading a thumbnail and a - * full-sized image, this will be [true] for the first image to - * load and [false] for the second. - * @return [true] if the listener has handled setting the resource on the target, - * [false] to allow Glide's request to update the target. - * Setting the resource includes handling animations, be sure to take that into account. - */ var onResourceReady: (( resource: T, model: Any?, @@ -55,36 +36,6 @@ class GlideRequestListenerWrapper { dataSource: DataSource?, isFirstResource: Boolean ) -> Boolean)? = null - /** - * Called when an exception occurs during a load, immediately before [Target.onLoadFailed]. - * Will only be called if we currently want to display an image for the given model - * in the given target. It is recommended to create a single instance - * per activity/fragment rather than instantiate a new object for each call to [Glide.load] - * to avoid object churn. - * - *

It is safe to reload this or a different model or change what is displayed in the target at - * this point. For example: - *

-     * {@code
-     * public void onLoadFailed(Exception e, T model, Target target, boolean isFirstResource) {
-     *     target.setPlaceholder(R.drawable.a_specific_error_for_my_exception);
-     *     Glide.load(model).into(target);
-     * }
-     * }
-     * 
- *

- * - *

Note - if you want to reload this or any other model after an exception, you will need to - * include all relevant builder calls (like centerCrop, placeholder etc). - * - * @param e The maybe [null] exception containing information about why the - * request failed. - * @param model The model we were trying to load when the exception occurred. - * @param target The [Target] we were trying to load the image into. - * @param isFirstResource [true] if this exception is for the first resource to load. - * @return [true] if the listener has handled updating the target for the given exception, - * [false] to allow Glide's request to update the target. - */ var onLoadFailed: ((e: GlideException?, model: Any?, target: Target?, isFirstResource: Boolean) -> Boolean)? = null } diff --git a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Keyboard.kt b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Keyboard.kt index c2c0922..f27278c 100644 --- a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Keyboard.kt +++ b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Keyboard.kt @@ -7,10 +7,6 @@ import android.graphics.Rect import android.view.View import android.view.inputmethod.InputMethodManager -/** - * @author jieyi - * @since 11/8/17 - */ inline fun View.hideSoftKeyboard() = run { (context.getSystemService(Context.INPUT_METHOD_SERVICE) as InputMethodManager) .hideSoftInputFromWindow(windowToken, 0) diff --git a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Listener.kt b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Listener.kt index 4458c65..ffb912c 100644 --- a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Listener.kt +++ b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Listener.kt @@ -2,11 +2,6 @@ package com.devrapid.kotlinknifer import android.animation.Animator -/** - * - * @author jieyi - * @since 6/12/17 - */ fun animatorListener(init: AnimatorListenerWrapper.() -> Unit): Animator.AnimatorListener { val wrapper = AnimatorListenerWrapper() @@ -15,9 +10,9 @@ fun animatorListener(init: AnimatorListenerWrapper.() -> Unit): Animator.Animato return onListener(wrapper) } - /** - * Using chain style for [animatorListener]. - */ +/** + * Using chain style for [animatorListener]. + */ typealias animatorWithSelf = AnimatorListener.(animator: Animator) -> Unit class AnimatorListener : Animator.AnimatorListener { @@ -40,9 +35,9 @@ class AnimatorListener : Animator.AnimatorListener { this.also { it.repeatFunction = onRepeatFun } } - /** - * Using DSL style for [animatorListener]. - */ +/** + * Using DSL style for [animatorListener]. + */ typealias animatorEmpty = (animator: Animator) -> Unit class AnimatorListenerWrapper { @@ -75,4 +70,4 @@ private fun onListener(wrapper: AnimatorListenerWrapper): Animator.AnimatorListe override fun onAnimationCancel(animator: Animator) = wrapper._cancel(animator) override fun onAnimationRepeat(animator: Animator) = wrapper._repeat(animator) } -} \ No newline at end of file +} diff --git a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Logs.kt b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Logs.kt index 7beb04c..a0720fc 100644 --- a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Logs.kt +++ b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Logs.kt @@ -2,20 +2,10 @@ package com.devrapid.kotlinknifer import android.util.Log -/** - * Log Module - * - * @author Jieyi - * @since 8/1/15 - */ fun logv(vararg msg: Any?) = Logs.v(*msg) - fun logd(vararg msg: Any?) = Logs.d(*msg) - fun logi(vararg msg: Any?) = Logs.i(*msg) - fun logw(vararg msg: Any?) = Logs.w(*msg) - fun loge(vararg msg: Any?) = Logs.e(*msg) internal object Logs { diff --git a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Network.kt b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Network.kt new file mode 100644 index 0000000..42142bc --- /dev/null +++ b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Network.kt @@ -0,0 +1,26 @@ +package com.devrapid.kotlinknifer + +import android.annotation.SuppressLint +import android.content.Context +import android.content.Context.CONNECTIVITY_SERVICE +import android.net.ConnectivityManager +import com.devrapid.kotlinshaver.cast +import com.devrapid.kotlinshaver.isNotNull + +@SuppressLint("MissingPermission") +fun Context.activeNetworkInfo() = + (getSystemService(Context.CONNECTIVITY_SERVICE) as ConnectivityManager).activeNetworkInfo + +fun Context.isWifiConnected() = activeNetworkInfo().run { isNotNull() && ConnectivityManager.TYPE_WIFI == type } + +fun Context.isConnected() = activeNetworkInfo().run { isNotNull() && isConnected } + +@SuppressLint("MissingPermission") +fun hasNetwork(context: Context): Boolean { + var isConnected = false // Initial Value + val connectivityManager = cast(context.getSystemService(CONNECTIVITY_SERVICE)) + val activeNetwork = connectivityManager.activeNetworkInfo + if (activeNetwork != null && activeNetwork.isConnected) + isConnected = true + return isConnected +} diff --git a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Resolution.kt b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Resolution.kt index db40b91..9cc74b4 100644 --- a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Resolution.kt +++ b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Resolution.kt @@ -5,10 +5,6 @@ import android.content.res.Resources import org.jetbrains.anko.px2dip import org.jetbrains.anko.px2sp -/** - * @author jieyi - * @since 11/24/17 - */ /** Convert dp to px */ fun Float.dp2px(context: Context) = this * context.resources.displayMetrics.density + 0.5f diff --git a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Screen.kt b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Screen.kt index f7e0fb6..e168641 100644 --- a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Screen.kt +++ b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Screen.kt @@ -3,10 +3,6 @@ package com.devrapid.kotlinknifer import android.app.Activity import android.util.DisplayMetrics -/** - * @author Jieyi Wu - * @since 2018/03/05 - */ /** * Obtain the screen size in pixels. * @@ -14,4 +10,4 @@ import android.util.DisplayMetrics */ fun Activity.displayPixels() = DisplayMetrics().also { windowManager.defaultDisplay.getMetrics(it) -}.run { widthPixels to heightPixels } \ No newline at end of file +}.run { widthPixels to heightPixels } diff --git a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Spannable.kt b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Spannable.kt new file mode 100644 index 0000000..29604a2 --- /dev/null +++ b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Spannable.kt @@ -0,0 +1,27 @@ +package com.devrapid.kotlinknifer + +import android.text.Html +import android.text.method.LinkMovementMethod +import android.text.style.ClickableSpan +import android.view.View +import android.widget.TextView +import androidx.core.text.HtmlCompat +import androidx.core.text.parseAsHtml + +inline fun TextView.withMovement() = apply { + movementMethod = LinkMovementMethod.getInstance() +} + +inline fun TextView.parseAsHtml( + flags: Int = HtmlCompat.FROM_HTML_MODE_LEGACY, + imageGetter: Html.ImageGetter? = null, + tagHandler: Html.TagHandler? = null +) = apply { + text = text.toString().parseAsHtml(flags, imageGetter, tagHandler) +} + +fun clickableSpan(block: (widget: View) -> Unit) = object : ClickableSpan() { + override fun onClick(widget: View) { + block(widget) + } +} diff --git a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Toast.kt b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Toast.kt new file mode 100644 index 0000000..e9f04bc --- /dev/null +++ b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/Toast.kt @@ -0,0 +1,16 @@ +package com.devrapid.kotlinknifer + +import android.content.Context +import android.view.Gravity +import android.view.LayoutInflater +import android.widget.TextView +import android.widget.Toast + +fun Context.buildCustomToast(customLayoutId: Int, tvId: Int, msg: String, durationTime: Int = Toast.LENGTH_SHORT) = + Toast(this).apply { + setGravity(Gravity.BOTTOM, 0, 16.dp2px(this@buildCustomToast).toInt()) + duration = durationTime + view = LayoutInflater.from(view.context).inflate(customLayoutId, null).apply { + findViewById(tvId).apply { text = msg } + } + } diff --git a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/View.kt b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/View.kt index 7f80c26..c3c2465 100644 --- a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/View.kt +++ b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/View.kt @@ -18,10 +18,6 @@ import androidx.annotation.ColorRes import androidx.appcompat.app.AlertDialog import com.example.kotlinknifer.R -/** - * @author jieyi - * @since 4/12/17 - */ inline fun View.resizeView(width: Int? = null, height: Int? = null) { val newLayoutParams = layoutParams?.apply { height?.let { this.height = it } @@ -100,10 +96,10 @@ inline fun Activity.statusBarHeight() = Rect() .top fun Activity.changeStatusBarColorRes(@ColorRes colorRes: Int) = - setStatusBarColorBy { statusBarColor = getResColor(colorRes) } + setStatusBarColorBy { statusBarColor = getColorBy(colorRes) } fun Activity.changeStatusBarColor(@ColorInt color: Int, ratio: Float = 1f) = - setStatusBarColorBy { statusBarColor = getColorWithAlpha(color, ratio) } + setStatusBarColorBy { statusBarColor = ofAlpha(color, ratio) } internal inline fun Activity.setStatusBarColorBy(block: Window.() -> Unit) { if (Build.VERSION_CODES.LOLLIPOP <= Build.VERSION.SDK_INT) diff --git a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/ViewStub.kt b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/ViewStub.kt new file mode 100644 index 0000000..827285e --- /dev/null +++ b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/ViewStub.kt @@ -0,0 +1,28 @@ +package com.devrapid.kotlinknifer + +import android.app.Activity +import android.view.View +import androidx.annotation.IdRes +import androidx.fragment.app.Fragment + +fun Activity.obtainViewStub(@IdRes stub: Int, @IdRes realView: Int) = + (findViewById(stub) as? View) ?: findViewById(realView) + +fun Fragment.obtainViewStub(@IdRes stub: Int, @IdRes realView: Int) = + (requireNotNull(view).findViewById(stub) as? View) ?: requireNotNull(view).findViewById(realView) + +fun Activity.showViewStub(@IdRes stub: Int, @IdRes realView: Int, options: (View.() -> Unit)? = null) { + obtainViewStub(stub, realView).apply { + visible() + bringToFront() + options?.let(this::apply) + } +} + +fun Fragment.showViewStub(@IdRes stub: Int, @IdRes realView: Int, options: (View.() -> Unit)? = null) { + obtainViewStub(stub, realView).apply { + visible() + bringToFront() + options?.let(this::apply) + } +} diff --git a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/recyclerview/Extensions.kt b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/recyclerview/Extensions.kt new file mode 100644 index 0000000..162dfc6 --- /dev/null +++ b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/recyclerview/Extensions.kt @@ -0,0 +1,13 @@ +package com.devrapid.kotlinknifer.recyclerview + +import android.content.Context +import android.util.DisplayMetrics +import androidx.recyclerview.widget.LinearSmoothScroller +import androidx.recyclerview.widget.RecyclerView + +class SlowlySmoothScroller(context: Context) : LinearSmoothScroller(context) { + override fun calculateSpeedPerPixel(displayMetrics: DisplayMetrics) = .25f +} + +fun RecyclerView.LayoutManager.smoothScrollTo(smoothScroller: LinearSmoothScroller, position: Int) = + startSmoothScroll(smoothScroller.apply { targetPosition = position }) diff --git a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/recyclerview/WrapContentLinearLayoutManager.kt b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/recyclerview/WrapContentLinearLayoutManager.kt index b6462c5..26fb022 100644 --- a/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/recyclerview/WrapContentLinearLayoutManager.kt +++ b/kotlinknifer/src/main/java/com/devrapid/kotlinknifer/recyclerview/WrapContentLinearLayoutManager.kt @@ -7,12 +7,6 @@ import androidx.recyclerview.widget.RecyclerView import com.devrapid.kotlinknifer.loge import com.devrapid.kotlinknifer.logw -/** - * Wrapper the linear layout manager for catching the exceptions and don't make app crash. - * - * @author jieyi - * @since 2018/01/09 - */ class WrapContentLinearLayoutManager : LinearLayoutManager { constructor(context: Context) : super(context) constructor(context: Context, orientation: Int, reverseLayout: Boolean) : super(context, orientation, reverseLayout) diff --git a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/ArrayList.kt b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/ArrayList.kt index 9d8fbf4..5e0fa24 100644 --- a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/ArrayList.kt +++ b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/ArrayList.kt @@ -1,14 +1,10 @@ package com.devrapid.kotlinshaver -/** - * @author jieyi - * @since 11/8/17 - */ -fun ArrayList.removeRange(from: Int, to: Int): Boolean = - if (!(from in 0 until size && to in 0 until size && from > to)) { +fun ArrayList.removeRange(range: IntRange) = + if (!(range.start in 0 until size && range.last in 0 until size && range.start > range.last)) { false } else { - subList(from, to).clear() + subList(range.start, range.last).clear() true } diff --git a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Casting.kt b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Casting.kt index 9df1da3..2a29207 100644 --- a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Casting.kt +++ b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Casting.kt @@ -1,6 +1,7 @@ package com.devrapid.kotlinshaver inline fun castOrNull(from: Any?) = from as? T + inline fun cast(from: Any?): T { if (null == from) throw NullPointerException("Null object can't cast.") diff --git a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Coroutine.kt b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Coroutine.kt index 83af68c..7c880a9 100644 --- a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Coroutine.kt +++ b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Coroutine.kt @@ -1,5 +1,3 @@ -@file:Suppress("NOTHING_TO_INLINE") - package com.devrapid.kotlinshaver import kotlinx.coroutines.CoroutineScope @@ -35,8 +33,8 @@ inline fun gAsync( noinline block: suspend CoroutineScope.() -> T ) = GlobalScope.async(context, start, block) -inline fun aUI(noinline block: suspend CoroutineScope.() -> T) = CoroutineScope(Main).async(block = block) +inline fun uiAsync(noinline block: suspend CoroutineScope.() -> T) = CoroutineScope(Main).async(block = block) -inline fun aBKG(noinline block: suspend CoroutineScope.() -> T) = CoroutineScope(Default).async(block = block) +inline fun bkgAsync(noinline block: suspend CoroutineScope.() -> T) = CoroutineScope(Default).async(block = block) -inline fun aIO(noinline block: suspend CoroutineScope.() -> T) = CoroutineScope(IO).async(block = block) +inline fun ioAsync(noinline block: suspend CoroutineScope.() -> T) = CoroutineScope(IO).async(block = block) diff --git a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Field.kt b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Field.kt index 32ca079..855d400 100644 --- a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Field.kt +++ b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Field.kt @@ -1,5 +1,3 @@ -@file:Suppress("NOTHING_TO_INLINE") - package com.devrapid.kotlinshaver import java.lang.reflect.Field diff --git a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Instance.kt b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Instance.kt index 6b61642..6328eb8 100644 --- a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Instance.kt +++ b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Instance.kt @@ -2,10 +2,5 @@ package com.devrapid.kotlinshaver -/** - * @author jieyi - * @since 2018/01/19 - */ /** This way might cost a little overhead. */ -inline fun List<*>.toInstance() = - filterIsInstance().takeIf { it.size == this.size } +inline fun List<*>.toInstance() = filterIsInstance().takeIf { it.size == this.size } diff --git a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Int.kt b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Int.kt index 90e3b75..9a58e9a 100644 --- a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Int.kt +++ b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Int.kt @@ -1,5 +1,3 @@ -@file:Suppress("NOTHING_TO_INLINE") - package com.devrapid.kotlinshaver inline fun Int.toBool() = 0 < this diff --git a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Kits.kt b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Kits.kt index 5bdd885..89f2fbb 100644 --- a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Kits.kt +++ b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Kits.kt @@ -5,11 +5,6 @@ package com.devrapid.kotlinshaver import kotlin.contracts.ExperimentalContracts import kotlin.contracts.contract -/** - * - * @author jieyi - * @since 7/28/17 - */ inline infix fun (() -> Unit).iff(condition: Any?): Any? { return when (condition) { is Boolean -> if (condition) this() else null diff --git a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/String.kt b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/String.kt index 17476af..389f004 100644 --- a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/String.kt +++ b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/String.kt @@ -1,15 +1,9 @@ -@file:Suppress("NOTHING_TO_INLINE") - package com.devrapid.kotlinshaver import java.text.DecimalFormat import java.text.NumberFormat import java.util.Locale -/** - * @author jieyi - * @since 11/8/17 - */ inline fun String.formatToMoneyKarma() = DecimalFormat("###,###").format(java.lang.Double.parseDouble(this)) inline fun Long.toMoneyFormat(locale: Locale?) = @@ -23,3 +17,5 @@ inline fun Long.toMoneyFormatWithCurrency(locale: Locale?) = inline fun Double.toMoneyFormatWithCurrency(locale: Locale?) = (locale?.let(NumberFormat::getCurrencyInstance) ?: NumberFormat.getCurrencyInstance()).format(this) + +fun String.trimMarginAndNewLine() = trimMargin().replace("\n", "") diff --git a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Thread.kt b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Thread.kt index 94f0487..164e185 100644 --- a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Thread.kt +++ b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Thread.kt @@ -1,9 +1,3 @@ -@file:Suppress("NOTHING_TO_INLINE") - package com.devrapid.kotlinshaver -/** - * @author jieyi - * @since 11/8/17 - */ -inline fun threadName(): String = Thread.currentThread().name \ No newline at end of file +inline fun threadName() = Thread.currentThread().name diff --git a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Time.kt b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Time.kt index 5489a46..728230e 100644 --- a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Time.kt +++ b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Time.kt @@ -1,15 +1,22 @@ -@file:Suppress("NOTHING_TO_INLINE") - package com.devrapid.kotlinshaver -/** - * Time extension tool. - * - * @author jieyi - * @since 9/8/17 - */ +import java.text.SimpleDateFormat +import java.util.Date +import java.util.Locale + +const val DATE_YYYY_MM_DD = "yyyyMMdd" +const val DATE_YYYY_MM_DD_WITH_SLASH = "yyyy/MM/dd" +const val DATE_YYYY_MM_DD_WITH_DASH = "yyyy-MM-dd" +const val DATE_YYYY_MM_DD_WITH_DOT = "yyyy.MM.dd" + inline fun Int.format(digits: Int) = String.format("%0${digits}d", this) -inline fun Int.toTimeString(): String = "${(this / 60).format(2)}:${(this % 60).format(2)}" +inline fun Int.toTimeString() = "${(this / 60).format(2)}:${(this % 60).format(2)}" + +inline fun String.toDate(pattern: String = DATE_YYYY_MM_DD, locale: Locale = Locale.US) = + SimpleDateFormat(pattern, locale).parse(this) + +inline fun Date.asString(pattern: String = DATE_YYYY_MM_DD_WITH_SLASH, locale: Locale = Locale.US) = + SimpleDateFormat(pattern, locale).format(this) val currentTime get() = System.currentTimeMillis() diff --git a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/TypeAliases.kt b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/TypeAliases.kt new file mode 100644 index 0000000..934c6c1 --- /dev/null +++ b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/TypeAliases.kt @@ -0,0 +1,8 @@ +package com.devrapid.kotlinshaver + +typealias UniqueId = Long + +// Generic with Type Parameters +typealias LookUp = HashMap + +typealias Token = String diff --git a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Completable.kt b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/rxjava2/Completable.kt similarity index 89% rename from kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Completable.kt rename to kotlinshaver/src/main/java/com/devrapid/kotlinshaver/rxjava2/Completable.kt index c57e546..1a94518 100644 --- a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Completable.kt +++ b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/rxjava2/Completable.kt @@ -1,13 +1,9 @@ -package com.devrapid.kotlinshaver +package com.devrapid.kotlinshaver.rxjava2 import io.reactivex.CompletableObserver import io.reactivex.disposables.Disposable -/** - * @author Jieyi Wu - * @since 2018/03/25 - */ -fun completableObserver(): CompletablePlugin = CompletablePlugin() +fun completableObserver() = CompletablePlugin() fun completableObserver( onError: (Throwable) -> Unit = {}, diff --git a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Observable.kt b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/rxjava2/Observable.kt similarity index 95% rename from kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Observable.kt rename to kotlinshaver/src/main/java/com/devrapid/kotlinshaver/rxjava2/Observable.kt index b3bea7b..bb16926 100644 --- a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Observable.kt +++ b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/rxjava2/Observable.kt @@ -1,6 +1,6 @@ @file:Suppress("NOTHING_TO_INLINE") -package com.devrapid.kotlinshaver +package com.devrapid.kotlinshaver.rxjava2 import io.reactivex.BackpressureStrategy import io.reactivex.Completable @@ -20,11 +20,6 @@ import io.reactivex.internal.operators.observable.ObservableCreate import io.reactivex.internal.operators.single.SingleCreate import io.reactivex.subjects.PublishSubject -/** - * - * @author jieyi - * @since 9/8/17 - */ inline fun observable(crossinline body: (ObservableEmitter) -> Unit): Observable = ObservableCreate { body(it) } diff --git a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Observer.kt b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/rxjava2/Observer.kt similarity index 90% rename from kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Observer.kt rename to kotlinshaver/src/main/java/com/devrapid/kotlinshaver/rxjava2/Observer.kt index c59b832..17ed029 100644 --- a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Observer.kt +++ b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/rxjava2/Observer.kt @@ -1,15 +1,9 @@ -package com.devrapid.kotlinshaver +package com.devrapid.kotlinshaver.rxjava2 import io.reactivex.Observer import io.reactivex.disposables.Disposable -/** - * RxJava2 extension tool. - * - * @author jieyi - * @since 9/8/17 - */ -fun observer(): ObserverPlugin = ObserverPlugin() +fun observer() = ObserverPlugin() fun observer( onError: (Throwable) -> Unit = {}, diff --git a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Single.kt b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/rxjava2/Single.kt similarity index 90% rename from kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Single.kt rename to kotlinshaver/src/main/java/com/devrapid/kotlinshaver/rxjava2/Single.kt index 1ff4073..d3a02c6 100644 --- a/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/Single.kt +++ b/kotlinshaver/src/main/java/com/devrapid/kotlinshaver/rxjava2/Single.kt @@ -1,13 +1,9 @@ -package com.devrapid.kotlinshaver +package com.devrapid.kotlinshaver.rxjava2 import io.reactivex.SingleObserver import io.reactivex.disposables.Disposable -/** - * @author Jieyi Wu - * @since 2018/03/25 - */ -fun singleObserver(): SinglePlugin = SinglePlugin() +fun singleObserver() = SinglePlugin() fun singleObserver( onError: (Throwable) -> Unit = {},