From fb9ca21757068c0fb4123a5e30b1471ae4c32cf3 Mon Sep 17 00:00:00 2001 From: Allan Wang Date: Sun, 10 Dec 2017 23:39:57 -0500 Subject: Unify start activity design (#112) --- .travis.yml | 4 +- .../kotlin/ca/allanwang/kau/about/AboutBinder.kt | 5 ++- .../kotlin/ca/allanwang/kau/utils/ActivityUtils.kt | 25 ++++++------ .../kotlin/ca/allanwang/kau/utils/BundleUtils.kt | 46 ++++++++++++++++++++++ .../kotlin/ca/allanwang/kau/utils/ContextUtils.kt | 40 +++---------------- .../kotlin/ca/allanwang/kau/utils/FileUtils.kt | 1 + .../main/kotlin/ca/allanwang/kau/utils/Utils.kt | 10 +---- gradle.properties | 2 +- .../allanwang/kau/mediapicker/MediaPickerBinder.kt | 6 ++- .../kotlin/ca/allanwang/kau/sample/AnimActivity.kt | 12 +++--- .../kotlin/ca/allanwang/kau/sample/MainActivity.kt | 7 +++- 11 files changed, 89 insertions(+), 69 deletions(-) create mode 100644 core/src/main/kotlin/ca/allanwang/kau/utils/BundleUtils.kt diff --git a/.travis.yml b/.travis.yml index a03abc8..fcbb2d3 100644 --- a/.travis.yml +++ b/.travis.yml @@ -7,13 +7,15 @@ android: # - android-21 - platform-tools - tools - - build-tools-27.0.1 + - build-tools-27.0.2 - android-27 - extra-android-support - extra-android-m2repository - extra-google-m2repository licenses: - ".+" +before_install: +- yes | sdkmanager "platforms;android-27" #before_script: #- echo no | android create avd --force -n test -t android-21 --abi armeabi-v7a #- emulator -avd test -no-audio -no-window & diff --git a/about/src/main/kotlin/ca/allanwang/kau/about/AboutBinder.kt b/about/src/main/kotlin/ca/allanwang/kau/about/AboutBinder.kt index 902f6e5..0380479 100644 --- a/about/src/main/kotlin/ca/allanwang/kau/about/AboutBinder.kt +++ b/about/src/main/kotlin/ca/allanwang/kau/about/AboutBinder.kt @@ -2,6 +2,7 @@ package ca.allanwang.kau.about import android.app.Activity import ca.allanwang.kau.utils.startActivity +import ca.allanwang.kau.utils.withSceneTransitionAnimation /** * Created by Allan Wang on 2017-07-22. @@ -11,5 +12,7 @@ import ca.allanwang.kau.utils.startActivity * About activity launcher */ fun Activity.kauLaunchAbout(clazz: Class) { - startActivity(clazz, transition = true) + startActivity(clazz, bundleBuilder = { + withSceneTransitionAnimation(this@kauLaunchAbout) + }) } \ No newline at end of file diff --git a/core/src/main/kotlin/ca/allanwang/kau/utils/ActivityUtils.kt b/core/src/main/kotlin/ca/allanwang/kau/utils/ActivityUtils.kt index 0e418ec..90961c5 100644 --- a/core/src/main/kotlin/ca/allanwang/kau/utils/ActivityUtils.kt +++ b/core/src/main/kotlin/ca/allanwang/kau/utils/ActivityUtils.kt @@ -2,7 +2,6 @@ package ca.allanwang.kau.utils import android.annotation.SuppressLint import android.app.Activity -import android.app.ActivityOptions import android.content.Context import android.content.Intent import android.graphics.Color @@ -20,35 +19,35 @@ import org.jetbrains.anko.contentView * Created by Allan Wang on 2017-06-21. */ +@DslMarker +@Target(AnnotationTarget.CLASS, AnnotationTarget.TYPE, AnnotationTarget.FUNCTION) +annotation class KauActivity + /** * Helper class to launch an activity for result * Counterpart of [Activity.startActivityForResult] * For starting activities without result, see [startActivity] */ -@SuppressLint("NewApi") -fun Activity.startActivityForResult( +inline fun Activity.startActivityForResult( clazz: Class, requestCode: Int, - transition: Boolean = false, - bundle: Bundle? = null, + bundleBuilder: Bundle.() -> Unit = {}, intentBuilder: Intent.() -> Unit = {}) { val intent = Intent(this, clazz) - val fullBundle = Bundle() - if (transition && buildIsLollipopAndUp) - fullBundle.with(ActivityOptions.makeSceneTransitionAnimation(this).toBundle()) - if (bundle != null) fullBundle.putAll(bundle) intent.intentBuilder() - startActivityForResult(intent, requestCode, if (fullBundle.isEmpty) null else fullBundle) + val bundle = Bundle() + bundle.bundleBuilder() + startActivityForResult(intent, requestCode, bundle) } /** * Restarts an activity from itself with a fade animation - * Keeps its existing extra bundles and has a builder to accept other parameters + * Keeps its existing extra bundles and has a intentBuilder to accept other parameters */ -fun Activity.restart(builder: Intent.() -> Unit = {}) { +inline fun Activity.restart(intentBuilder: Intent.() -> Unit = {}) { val i = Intent(this, this::class.java) i.putExtras(intent.extras) - i.builder() + i.intentBuilder() startActivity(i) overridePendingTransition(R.anim.kau_fade_in, R.anim.kau_fade_out) //No transitions finish() diff --git a/core/src/main/kotlin/ca/allanwang/kau/utils/BundleUtils.kt b/core/src/main/kotlin/ca/allanwang/kau/utils/BundleUtils.kt new file mode 100644 index 0000000..98fceaf --- /dev/null +++ b/core/src/main/kotlin/ca/allanwang/kau/utils/BundleUtils.kt @@ -0,0 +1,46 @@ +package ca.allanwang.kau.utils + +import android.annotation.SuppressLint +import android.app.Activity +import android.app.ActivityOptions +import android.content.Context +import android.os.Bundle +import android.support.annotation.AnimRes +import android.support.v4.app.ActivityOptionsCompat +import ca.allanwang.kau.R + +/** + * Created by Allan Wang on 10/12/17. + */ +/** + * Similar to [Bundle.putAll], but checks for a null insert and returns the parent bundle + */ +infix fun Bundle.with(bundle: Bundle?): Bundle { + if (bundle != null) putAll(bundle) + return this +} + +/** + * Adds transition bundle if context is activity and build is lollipop+ + */ +@SuppressLint("NewApi") +fun Bundle.withSceneTransitionAnimation(context: Context) { + if (context !is Activity || !buildIsLollipopAndUp) return + this with ActivityOptions.makeSceneTransitionAnimation(context).toBundle() +} + +fun Bundle.withCustomAnimation(context: Context, + @AnimRes enterResId: Int, + @AnimRes exitResId: Int) { + this with ActivityOptionsCompat.makeCustomAnimation(context, + enterResId, exitResId).toBundle() +} + +fun Bundle.withSlideIn(context: Context) = withCustomAnimation(context, + R.anim.kau_slide_in_right, R.anim.kau_fade_out) + +fun Bundle.withSlideOut(context: Context) = withCustomAnimation(context, + R.anim.kau_fade_in, R.anim.kau_slide_out_right_top) + +fun Bundle.withFade(context: Context) = withCustomAnimation(context, + android.R.anim.fade_in, android.R.anim.fade_out) \ No newline at end of file diff --git a/core/src/main/kotlin/ca/allanwang/kau/utils/ContextUtils.kt b/core/src/main/kotlin/ca/allanwang/kau/utils/ContextUtils.kt index 545a3f0..06b9601 100644 --- a/core/src/main/kotlin/ca/allanwang/kau/utils/ContextUtils.kt +++ b/core/src/main/kotlin/ca/allanwang/kau/utils/ContextUtils.kt @@ -2,9 +2,7 @@ package ca.allanwang.kau.utils -import android.annotation.SuppressLint import android.app.Activity -import android.app.ActivityOptions import android.content.ClipData import android.content.ClipboardManager import android.content.Context @@ -14,7 +12,6 @@ import android.graphics.drawable.Drawable import android.net.Uri import android.os.Bundle import android.support.annotation.* -import android.support.v4.app.ActivityOptionsCompat import android.support.v4.content.ContextCompat import android.util.TypedValue import android.view.View @@ -34,47 +31,20 @@ import com.afollestad.materialdialogs.MaterialDialog * Counterpart of [ContextCompat.startActivity] * For starting activities for results, see [startActivityForResult] */ -@SuppressLint("NewApi") -fun Context.startActivity( +inline fun Context.startActivity( clazz: Class, clearStack: Boolean = false, - transition: Boolean = false, - bundle: Bundle? = null, + bundleBuilder: Bundle.() -> Unit = {}, intentBuilder: Intent.() -> Unit = {}) { val intent = Intent(this, clazz) if (clearStack) intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TASK or Intent.FLAG_ACTIVITY_NEW_TASK) - val fullBundle = Bundle() - if (transition && this is Activity && buildIsLollipopAndUp) - fullBundle.with(ActivityOptions.makeSceneTransitionAnimation(this).toBundle()) - if (transition && this !is Activity) KL.d("Cannot make scene transition when context is not an instance of an Activity") - if (bundle != null) fullBundle.putAll(bundle) intent.intentBuilder() - ContextCompat.startActivity(this, intent, if (fullBundle.isEmpty) null else fullBundle) + val bundle = Bundle() + bundle.bundleBuilder() + ContextCompat.startActivity(this, intent, bundle) if (this is Activity && clearStack) finish() } -/** - * Bring in activity from the right - */ -fun Context.startActivitySlideIn(clazz: Class, clearStack: Boolean = false, intentBuilder: Intent.() -> Unit = {}, bundleBuilder: Bundle.() -> Unit = {}) { - val fullBundle = Bundle() - fullBundle.with(ActivityOptionsCompat.makeCustomAnimation(this, R.anim.kau_slide_in_right, R.anim.kau_fade_out).toBundle()) - fullBundle.bundleBuilder() - startActivity(clazz, clearStack, intentBuilder = intentBuilder, bundle = if (fullBundle.isEmpty) null else fullBundle) -} - -/** - * Bring in activity from behind while pushing the current activity to the right - * This replicates the exit animation of a sliding activity, but is a forward creation - * For the animation to work, the previous activity should not be in the stack (otherwise you wouldn't need this in the first place) - * Consequently, the stack will be cleared by default - */ -fun Context.startActivitySlideOut(clazz: Class, clearStack: Boolean = true, intentBuilder: Intent.() -> Unit = {}, bundleBuilder: Bundle.() -> Unit = {}) { - val fullBundle = Bundle() - fullBundle.with(ActivityOptionsCompat.makeCustomAnimation(this, R.anim.kau_fade_in, R.anim.kau_slide_out_right_top).toBundle()) - fullBundle.bundleBuilder() - startActivity(clazz, clearStack, intentBuilder = intentBuilder, bundle = if (fullBundle.isEmpty) null else fullBundle) -} fun Context.startPlayStoreLink(@StringRes packageIdRes: Int) = startPlayStoreLink(string(packageIdRes)) diff --git a/core/src/main/kotlin/ca/allanwang/kau/utils/FileUtils.kt b/core/src/main/kotlin/ca/allanwang/kau/utils/FileUtils.kt index b97f4aa..65c28f7 100644 --- a/core/src/main/kotlin/ca/allanwang/kau/utils/FileUtils.kt +++ b/core/src/main/kotlin/ca/allanwang/kau/utils/FileUtils.kt @@ -1,5 +1,6 @@ package ca.allanwang.kau.utils +import android.os.Bundle import java.io.File import java.io.InputStream diff --git a/core/src/main/kotlin/ca/allanwang/kau/utils/Utils.kt b/core/src/main/kotlin/ca/allanwang/kau/utils/Utils.kt index 954bedc..8b32894 100644 --- a/core/src/main/kotlin/ca/allanwang/kau/utils/Utils.kt +++ b/core/src/main/kotlin/ca/allanwang/kau/utils/Utils.kt @@ -126,12 +126,4 @@ class KauException(message: String) : RuntimeException(message) fun String.withMaxLength(n: Int): String = if (length <= n) this - else substring(0, n - 1) + KAU_ELLIPSIS - -/** - * Similar to [Bundle.putAll], but checks for a null insert and returns the parent bundle - */ -fun Bundle.with(bundle: Bundle?): Bundle { - if (bundle != null) putAll(bundle) - return this -} \ No newline at end of file + else substring(0, n - 1) + KAU_ELLIPSIS \ No newline at end of file diff --git a/gradle.properties b/gradle.properties index e9c7540..6376084 100644 --- a/gradle.properties +++ b/gradle.properties @@ -20,7 +20,7 @@ APP_GROUP=ca.allanwang CORE_MIN_SDK=19 MIN_SDK=21 TARGET_SDK=27 -BUILD_TOOLS=27.0.1 +BUILD_TOOLS=27.0.2 ANDROID_SUPPORT_LIBS=27.0.2 VERSION_NAME=3.5.1.0 diff --git a/mediapicker/src/main/kotlin/ca/allanwang/kau/mediapicker/MediaPickerBinder.kt b/mediapicker/src/main/kotlin/ca/allanwang/kau/mediapicker/MediaPickerBinder.kt index cb218fc..bf58a30 100644 --- a/mediapicker/src/main/kotlin/ca/allanwang/kau/mediapicker/MediaPickerBinder.kt +++ b/mediapicker/src/main/kotlin/ca/allanwang/kau/mediapicker/MediaPickerBinder.kt @@ -4,6 +4,7 @@ import android.app.Activity import android.content.Context import android.content.Intent import ca.allanwang.kau.utils.startActivityForResult +import ca.allanwang.kau.utils.withSceneTransitionAnimation import com.bumptech.glide.RequestBuilder import com.bumptech.glide.load.engine.DiskCacheStrategy import com.bumptech.glide.request.RequestOptions @@ -19,7 +20,10 @@ import com.bumptech.glide.request.RequestOptions * Image picker launchers */ fun Activity.kauLaunchMediaPicker(clazz: Class>, requestCode: Int) { - startActivityForResult(clazz, requestCode, transition = MediaPickerActivityOverlayBase::class.java.isAssignableFrom(clazz)) + startActivityForResult(clazz, requestCode, bundleBuilder = { + if (MediaPickerActivityOverlayBase::class.java.isAssignableFrom(clazz)) + withSceneTransitionAnimation(this@kauLaunchMediaPicker) + }) } /** diff --git a/sample/src/main/kotlin/ca/allanwang/kau/sample/AnimActivity.kt b/sample/src/main/kotlin/ca/allanwang/kau/sample/AnimActivity.kt index f052d97..3f25ac3 100644 --- a/sample/src/main/kotlin/ca/allanwang/kau/sample/AnimActivity.kt +++ b/sample/src/main/kotlin/ca/allanwang/kau/sample/AnimActivity.kt @@ -10,10 +10,7 @@ import ca.allanwang.kau.permissions.kauRequestPermissions import ca.allanwang.kau.swipe.SWIPE_EDGE_LEFT import ca.allanwang.kau.swipe.kauSwipeOnCreate import ca.allanwang.kau.swipe.kauSwipeOnDestroy -import ca.allanwang.kau.utils.fullLinearRecycler -import ca.allanwang.kau.utils.startActivitySlideOut -import ca.allanwang.kau.utils.toast -import ca.allanwang.kau.utils.withAlpha +import ca.allanwang.kau.utils.* import com.mikepenz.fastadapter.commons.adapters.FastItemAdapter /** @@ -36,8 +33,7 @@ class AnimActivity : KauBaseActivity() { ).map { PermissionCheckbox(it) }) adapter.withOnClickListener { _, _, item, _ -> KL.d("Perm Click") - kauRequestPermissions(item.permission) { - granted, _ -> + kauRequestPermissions(item.permission) { granted, _ -> toast("${item.permission} enabled: $granted") adapter.notifyAdapterDataSetChanged() } @@ -54,7 +50,9 @@ class AnimActivity : KauBaseActivity() { } override fun onBackPressed() { - startActivitySlideOut(MainActivity::class.java) + startActivity(MainActivity::class.java, bundleBuilder = { + withSlideOut(this@AnimActivity) + }) } } \ No newline at end of file diff --git a/sample/src/main/kotlin/ca/allanwang/kau/sample/MainActivity.kt b/sample/src/main/kotlin/ca/allanwang/kau/sample/MainActivity.kt index 482c911..dd81ce1 100644 --- a/sample/src/main/kotlin/ca/allanwang/kau/sample/MainActivity.kt +++ b/sample/src/main/kotlin/ca/allanwang/kau/sample/MainActivity.kt @@ -173,7 +173,12 @@ class MainActivity : KPrefActivity() { } plainText(R.string.adapter_showcase) { - onClick = { _, _, _ -> startActivity(AdapterActivity::class.java, transition = true); false } + onClick = { _, _, _ -> + startActivity(AdapterActivity::class.java, bundleBuilder = { + withSceneTransitionAnimation(this@MainActivity) + }) + false + } } plainText(R.string.kau_about_app) { -- cgit v1.2.3