[Debug] Add new debug mode. Include hidden Chucker in release.

This commit is contained in:
Kuba Szczodrzyński 2020-02-26 20:37:55 +01:00
parent d5863485f9
commit f6f1370edf
11 changed files with 132 additions and 6 deletions

View File

@ -166,8 +166,8 @@ dependencies {
//implementation project(":Navigation") //implementation project(":Navigation")
implementation project(":szkolny-font") implementation project(":szkolny-font")
debugImplementation "com.github.ChuckerTeam.Chucker:library:3.0.1" implementation "com.github.ChuckerTeam.Chucker:library:3.0.1"
releaseImplementation "com.github.ChuckerTeam.Chucker:library-no-op:3.0.1" //releaseImplementation "com.github.ChuckerTeam.Chucker:library-no-op:3.0.1"
//implementation 'com.github.wulkanowy:uonet-request-signer:master-SNAPSHOT' //implementation 'com.github.wulkanowy:uonet-request-signer:master-SNAPSHOT'
//implementation 'com.github.kuba2k2.uonet-request-signer:android:master-63f094b14a-1' //implementation 'com.github.kuba2k2.uonet-request-signer:android:master-63f094b14a-1'

View File

@ -60,6 +60,7 @@ class App : MultiDexApplication(), Configuration.Provider, CoroutineScope {
get() = profile.id get() = profile.id
var devMode = false var devMode = false
var debugMode = false
} }
val notificationChannelsManager by lazy { NotificationChannelsManager(this) } val notificationChannelsManager by lazy { NotificationChannelsManager(this) }
@ -103,7 +104,7 @@ class App : MultiDexApplication(), Configuration.Provider, CoroutineScope {
.readTimeout(10, TimeUnit.SECONDS) .readTimeout(10, TimeUnit.SECONDS)
builder.installHttpsSupport(this) builder.installHttpsSupport(this)
if (devMode || BuildConfig.DEBUG) { if (debugMode || BuildConfig.DEBUG) {
HyperLog.initialize(this) HyperLog.initialize(this)
HyperLog.setLogLevel(Log.VERBOSE) HyperLog.setLogLevel(Log.VERBOSE)
HyperLog.setLogFormat(DebugLogFormat(this)) HyperLog.setLogFormat(DebugLogFormat(this))
@ -158,6 +159,7 @@ class App : MultiDexApplication(), Configuration.Provider, CoroutineScope {
Iconics.registerFont(SzkolnyFont) Iconics.registerFont(SzkolnyFont)
App.db = AppDb(this) App.db = AppDb(this)
Themes.themeInt = config.ui.theme Themes.themeInt = config.ui.theme
debugMode = config.debugMode
MHttp.instance().customOkHttpClient(http) MHttp.instance().customOkHttpClient(http)
if (!profileLoadById(config.lastProfileId)) { if (!profileLoadById(config.lastProfileId)) {
@ -174,6 +176,7 @@ class App : MultiDexApplication(), Configuration.Provider, CoroutineScope {
if (config.devModePassword != null) if (config.devModePassword != null)
checkDevModePassword() checkDevModePassword()
debugMode = devMode || config.debugMode
if (config.sync.enabled) if (config.sync.enabled)
SyncWorker.scheduleNext(this@App, false) SyncWorker.scheduleNext(this@App, false)

View File

@ -75,6 +75,11 @@ class Config(val db: AppDb) : CoroutineScope, AbstractConfig {
get() { mPrivacyPolicyAccepted = mPrivacyPolicyAccepted ?: values.get("privacyPolicyAccepted", false); return mPrivacyPolicyAccepted ?: false } get() { mPrivacyPolicyAccepted = mPrivacyPolicyAccepted ?: values.get("privacyPolicyAccepted", false); return mPrivacyPolicyAccepted ?: false }
set(value) { set("privacyPolicyAccepted", value); mPrivacyPolicyAccepted = value } set(value) { set("privacyPolicyAccepted", value); mPrivacyPolicyAccepted = value }
private var mDebugMode: Boolean? = null
var debugMode: Boolean
get() { mDebugMode = mDebugMode ?: values.get("debugMode", false); return mDebugMode ?: false }
set(value) { set("debugMode", value); mDebugMode = value }
private var mDevModePassword: String? = null private var mDevModePassword: String? = null
var devModePassword: String? var devModePassword: String?
get() { mDevModePassword = mDevModePassword ?: values.get("devModePassword", null as String?); return mDevModePassword } get() { mDevModePassword = mDevModePassword ?: values.get("devModePassword", null as String?); return mDevModePassword }

View File

@ -23,6 +23,7 @@ class LoginActivity : AppCompatActivity(), CoroutineScope {
private const val TAG = "LoginActivity" private const val TAG = "LoginActivity"
@JvmField @JvmField
var navOptions: NavOptions? = null var navOptions: NavOptions? = null
var thisOneIsTricky = 0
} }
private val app: App by lazy { applicationContext as App } private val app: App by lazy { applicationContext as App }
@ -73,6 +74,8 @@ class LoginActivity : AppCompatActivity(), CoroutineScope {
super.onCreate(savedInstanceState) super.onCreate(savedInstanceState)
setTheme(R.style.AppTheme_Light) setTheme(R.style.AppTheme_Light)
thisOneIsTricky = -1
navOptions = NavOptions.Builder() navOptions = NavOptions.Builder()
.setEnterAnim(R.anim.slide_in_right) .setEnterAnim(R.anim.slide_in_right)
.setExitAnim(R.anim.slide_out_left) .setExitAnim(R.anim.slide_out_left)

View File

@ -3,16 +3,25 @@ package pl.szczodrzynski.edziennik.ui.modules.login
import android.app.Activity import android.app.Activity
import android.content.Intent import android.content.Intent
import android.os.Bundle import android.os.Bundle
import android.os.Process
import android.view.LayoutInflater import android.view.LayoutInflater
import android.view.View import android.view.View
import android.view.ViewGroup import android.view.ViewGroup
import android.view.animation.AnimationUtils
import android.widget.CompoundButton import android.widget.CompoundButton
import androidx.fragment.app.Fragment import androidx.fragment.app.Fragment
import com.afollestad.materialdialogs.DialogAction
import com.afollestad.materialdialogs.MaterialDialog
import com.google.android.material.dialog.MaterialAlertDialogBuilder
import pl.szczodrzynski.edziennik.App import pl.szczodrzynski.edziennik.App
import pl.szczodrzynski.edziennik.R import pl.szczodrzynski.edziennik.R
import pl.szczodrzynski.edziennik.databinding.FragmentLoginChooserBinding import pl.szczodrzynski.edziennik.databinding.FragmentLoginChooserBinding
import pl.szczodrzynski.edziennik.onChange
import pl.szczodrzynski.edziennik.onClick import pl.szczodrzynski.edziennik.onClick
import pl.szczodrzynski.edziennik.ui.modules.feedback.FeedbackActivity import pl.szczodrzynski.edziennik.ui.modules.feedback.FeedbackActivity
import pl.szczodrzynski.edziennik.utils.Anim
import kotlin.system.exitProcess
class LoginChooserFragment : Fragment() { class LoginChooserFragment : Fragment() {
companion object { companion object {
@ -34,6 +43,20 @@ class LoginChooserFragment : Fragment() {
} }
override fun onViewCreated(view: View, savedInstanceState: Bundle?) { override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
b.topLogo.onClick {
if (LoginActivity.thisOneIsTricky <= -1) {
LoginActivity.thisOneIsTricky = 999
}
if (LoginActivity.thisOneIsTricky in 0..7) {
LoginActivity.thisOneIsTricky++
if (LoginActivity.thisOneIsTricky == 7) {
b.topLogo.startAnimation(AnimationUtils.loadAnimation(activity, R.anim.shake));
if (b.devMode.visibility != View.VISIBLE)
Anim.expand(b.devMode, 500, null);
LoginActivity.thisOneIsTricky = 3
}
}
}
b.loginMobidziennikLogo.onClick { nav.navigate(R.id.loginMobidziennikFragment, null, LoginActivity.navOptions) } b.loginMobidziennikLogo.onClick { nav.navigate(R.id.loginMobidziennikFragment, null, LoginActivity.navOptions) }
b.loginLibrusLogo.onClick { nav.navigate(R.id.loginLibrusFragment, null, LoginActivity.navOptions) } b.loginLibrusLogo.onClick { nav.navigate(R.id.loginLibrusFragment, null, LoginActivity.navOptions) }
b.loginVulcanLogo.onClick { nav.navigate(R.id.loginVulcanFragment, null, LoginActivity.navOptions) } b.loginVulcanLogo.onClick { nav.navigate(R.id.loginVulcanFragment, null, LoginActivity.navOptions) }
@ -61,6 +84,46 @@ class LoginChooserFragment : Fragment() {
} }
} }
b.devMode.visibility = if (App.debugMode) View.VISIBLE else View.GONE
b.devMode.onChange { v, isChecked ->
if (isChecked) {
MaterialDialog.Builder(activity)
.title(R.string.are_you_sure)
.content(R.string.dev_mode_enable_warning)
.positiveText(R.string.yes)
.negativeText(R.string.no)
.onPositive { _: MaterialDialog?, _: DialogAction? ->
app.config.debugMode = true
MaterialAlertDialogBuilder(activity)
.setTitle("Restart")
.setMessage("Wymagany restart aplikacji")
.setPositiveButton("OK") { _, _ ->
Process.killProcess(Process.myPid())
Runtime.getRuntime().exit(0)
exitProcess(0)
}
.setCancelable(false)
.show()
/*if (b.devModeLayout.getVisibility() !== View.VISIBLE) {
Anim.expand(b.devModeTitle, 500, null)
Anim.expand(b.devModeLayout, 500, null)
}*/
}
.onNegative { _: MaterialDialog?, _: DialogAction? ->
b.devMode.isChecked = app.config.debugMode
b.devMode.jumpDrawablesToCurrentState()
Anim.collapse(b.devMode, 1000, null)
}
.show()
} else {
app.config.debugMode = false
/*if (b.devModeLayout.getVisibility() === View.VISIBLE) {
Anim.collapse(b.devModeTitle, 500, null)
Anim.collapse(b.devModeLayout, 500, null)
}*/
}
}
b.fakeLogin.visibility = if (App.devMode) View.VISIBLE else View.GONE b.fakeLogin.visibility = if (App.devMode) View.VISIBLE else View.GONE
b.fakeLogin.isChecked = fakeLogin b.fakeLogin.isChecked = fakeLogin
b.fakeLogin.setOnCheckedChangeListener { _: CompoundButton?, isChecked: Boolean -> b.fakeLogin.setOnCheckedChangeListener { _: CompoundButton?, isChecked: Boolean ->
@ -69,4 +132,4 @@ class LoginChooserFragment : Fragment() {
b.helpButton.onClick { startActivity(Intent(activity, FeedbackActivity::class.java)) } b.helpButton.onClick { startActivity(Intent(activity, FeedbackActivity::class.java)) }
} }
} }

View File

@ -4,6 +4,9 @@
package pl.szczodrzynski.edziennik.ui.modules.login package pl.szczodrzynski.edziennik.ui.modules.login
import android.animation.ArgbEvaluator
import android.animation.ObjectAnimator
import android.graphics.Color
import android.os.Bundle import android.os.Bundle
import android.view.LayoutInflater import android.view.LayoutInflater
import android.view.View import android.view.View
@ -19,6 +22,7 @@ import pl.szczodrzynski.edziennik.databinding.FragmentLoginEdudziennikBinding
import java.util.* import java.util.*
import kotlin.coroutines.CoroutineContext import kotlin.coroutines.CoroutineContext
class LoginEdudziennikFragment : Fragment(), CoroutineScope { class LoginEdudziennikFragment : Fragment(), CoroutineScope {
companion object { companion object {
private const val TAG = "LoginEdudziennikFragment" private const val TAG = "LoginEdudziennikFragment"
@ -28,6 +32,7 @@ class LoginEdudziennikFragment : Fragment(), CoroutineScope {
private lateinit var activity: LoginActivity private lateinit var activity: LoginActivity
private lateinit var b: FragmentLoginEdudziennikBinding private lateinit var b: FragmentLoginEdudziennikBinding
private val nav by lazy { activity.nav } private val nav by lazy { activity.nav }
private var hehe = 0
private val job: Job = Job() private val job: Job = Job()
override val coroutineContext: CoroutineContext override val coroutineContext: CoroutineContext
@ -52,6 +57,29 @@ class LoginEdudziennikFragment : Fragment(), CoroutineScope {
} }
} }
b.topText.onClick {
if (LoginActivity.thisOneIsTricky != -1)
return@onClick
hehe++
if (hehe >= 5) {
LoginActivity.thisOneIsTricky = 3
val colorAnim = ObjectAnimator.ofInt(
b.topText,
"textColor",
Color.BLACK,
Color.RED,
Color.BLACK,
Color.RED,
Color.BLACK,
Color.RED,
Color.BLACK
)
colorAnim.setEvaluator(ArgbEvaluator())
colorAnim.duration = 1500L
colorAnim.start()
}
}
b.backButton.onClick { nav.navigateUp() } b.backButton.onClick { nav.navigateUp() }
b.loginButton.onClick { b.loginButton.onClick {

View File

@ -108,7 +108,7 @@ public class Utils {
public static List<String> debugLog = new ArrayList<>(); public static List<String> debugLog = new ArrayList<>();
public static void d(String TAG, String message) { public static void d(String TAG, String message) {
if (App.Companion.getDevMode()) { if (App.Companion.getDebugMode()) {
HyperLog.d("Szkolny/"+TAG, message); HyperLog.d("Szkolny/"+TAG, message);
//debugLog.add(TAG+": "+message); //debugLog.add(TAG+": "+message);
} }

View File

@ -0,0 +1,8 @@
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
<translate android:duration="150"
android:fromXDelta="-10%"
android:repeatCount="5"
android:repeatMode="reverse"
android:toXDelta="10%"/>
</set>

View File

@ -24,6 +24,7 @@
android:orientation="vertical"> android:orientation="vertical">
<com.mikepenz.iconics.view.IconicsImageView <com.mikepenz.iconics.view.IconicsImageView
android:id="@+id/topLogo"
android:layout_width="32dp" android:layout_width="32dp"
android:layout_height="32dp" android:layout_height="32dp"
android:layout_marginStart="24dp" android:layout_marginStart="24dp"
@ -58,6 +59,16 @@
android:layout_marginRight="24dp" android:layout_marginRight="24dp"
android:text="@string/login_startpage_subtitle" /> android:text="@string/login_startpage_subtitle" />
<CheckBox
android:id="@+id/devMode"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginStart="8dp"
android:layout_marginEnd="8dp"
android:visibility="gone"
android:text="@string/developer_mode"
tools:visibility="visible"/>
<LinearLayout <LinearLayout
android:layout_width="match_parent" android:layout_width="match_parent"
android:layout_height="wrap_content" android:layout_height="wrap_content"
@ -206,7 +217,9 @@
android:layout_marginLeft="24dp" android:layout_marginLeft="24dp"
android:layout_marginTop="16dp" android:layout_marginTop="16dp"
android:layout_marginRight="24dp" android:layout_marginRight="24dp"
android:text="Fake login" /> android:text="Fake login"
android:visibility="gone"
tools:visibility="visible"/>
</LinearLayout> </LinearLayout>

View File

@ -44,6 +44,7 @@
tools:srcCompat="@tools:sample/avatars" /> tools:srcCompat="@tools:sample/avatars" />
<TextView <TextView
android:id="@+id/topText"
android:layout_width="match_parent" android:layout_width="match_parent"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_marginLeft="24dp" android:layout_marginLeft="24dp"

View File

@ -1187,4 +1187,6 @@
<string name="dialog_notification_filter_text"><![CDATA[Zaznacz, które powiadomienia mają być pokazywane w systemie oraz w aplikacji.]]></string> <string name="dialog_notification_filter_text"><![CDATA[Zaznacz, które powiadomienia mają być pokazywane w systemie oraz w aplikacji.]]></string>
<string name="notification_filter_warning">Czy na pewno chcesz zastosować te ustawienia?\n\nNie będziesz widział informacji o niektórych danych, przez co możesz przeoczyć ważne komunikaty, wiadomości lub oceny.\n\nUstawienia zostaną zastosowane dla aktualnie otwartego profilu.</string> <string name="notification_filter_warning">Czy na pewno chcesz zastosować te ustawienia?\n\nNie będziesz widział informacji o niektórych danych, przez co możesz przeoczyć ważne komunikaty, wiadomości lub oceny.\n\nUstawienia zostaną zastosowane dla aktualnie otwartego profilu.</string>
<string name="dialog_day_lessons_info">%s - %s (%s lekcji - %s godzin %s minut)</string> <string name="dialog_day_lessons_info">%s - %s (%s lekcji - %s godzin %s minut)</string>
<string name="developer_mode">Developer mode</string>
<string name="dev_mode_enable_warning">Te ustawienia nie są przeznaczone dla zwykłych użytkowników, wyłącznie dla twórcy tej aplikacji.\n\nNie są nawet w żaden sposób opisane, nie wiadomo co robią, więc możesz nawet nie wiedzieć kiedy coś zepsujesz.\n\nWłączenie tych opcji może spowodować utratę danych w aplikacji, uszkodzenie twojego systemu lub nawet uruchomienie wirusa na baterii.\n\nLepiej uważaj.</string>
</resources> </resources>