Skip to content

Commit

Permalink
perf: use custom logger class (#577)
Browse files Browse the repository at this point in the history
## 📜 Description

Use own `Logger` class in Android.

## 💡 Motivation and Context

Using own logger instance has many advantages:
- we can implement internal implementation (like turn on/turn off logger
depending on certain conditions);
- we can change internals and forward logs to react-native js side if
needed;
- since it's our implementation we can change internals as we want and
don't change the functionality in every piece of the code;
- we can apply various optimization technique later on (such as inline
functions etc.).

So in this PR I'm introducing own `Logger` class and use it everywhere
in the code. The main advantage of this class is that it's active only
in debug mode and in release mode it will not send any logs (thus it'll
slightly improve performance) and will not reveal details about the
libraries that are used internally n the particular application.

Later on I may add even more optimizations, such as inline functions
etc.

Closes
#576

## 📢 Changelog

<!-- High level overview of important changes -->
<!-- For example: fixed status bar manipulation; added new types
declarations; -->
<!-- If your changes don't affect one of platform/language below - then
remove this platform/language -->

### Android

- added `Logger` class;
- use `Logger` everywhere as alternative to `Log`.

## 🤔 How Has This Been Tested?

<!-- Please describe in detail how you tested your changes. -->
<!-- Include details of your testing environment, and the tests you ran
to -->
<!-- see how your change affects other areas of the code, etc. -->

## 📸 Screenshots (if appropriate):

|Before|After|
|-------|-----|
|<img width="1202" alt="image"
src="https://github.com/user-attachments/assets/a1f735b7-a6b0-422d-88d6-ee433c815d30">|<img
width="1910" alt="image"
src="https://github.com/user-attachments/assets/016f89f7-f6eb-4e5f-9137-9761b70df15b">|

## 📝 Checklist

- [x] CI successfully passed
- [x] I added new mocks and corresponding unit-tests if library API was
changed
  • Loading branch information
kirillzyusko authored Sep 3, 2024
1 parent 961e8a1 commit 7c9c450
Show file tree
Hide file tree
Showing 8 changed files with 40 additions and 20 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -3,11 +3,11 @@ package com.reactnativekeyboardcontroller.extensions
import android.os.Build
import android.text.Editable
import android.text.TextWatcher
import android.util.Log
import android.view.View
import android.widget.EditText
import com.facebook.react.views.scroll.ReactScrollView
import com.facebook.react.views.textinput.ReactEditText
import com.reactnativekeyboardcontroller.log.Logger
import com.reactnativekeyboardcontroller.ui.FrameScheduler
import java.lang.reflect.Field
import kotlin.math.max
Expand Down Expand Up @@ -57,15 +57,15 @@ fun EditText.addOnTextChangedListener(action: (String) -> Unit): TextWatcher {

textWatchListeners.add(0, listener)
} else {
Log.w(
Logger.w(
javaClass.simpleName,
"Can not attach listener because `fieldValue` does not belong to `ArrayList<TextWatcher>`",
)
}
} catch (e: ClassCastException) {
Log.w(javaClass.simpleName, "Can not attach listener because casting failed: ${e.message}")
Logger.w(javaClass.simpleName, "Can not attach listener because casting failed: ${e.message}")
} catch (e: NoSuchFieldException) {
Log.w(javaClass.simpleName, "Can not attach listener because field `mListeners` not found: ${e.message}")
Logger.w(javaClass.simpleName, "Can not attach listener because field `mListeners` not found: ${e.message}")
}

return listener
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
package com.reactnativekeyboardcontroller.extensions

import android.util.Log
import com.facebook.react.bridge.ReactContext
import com.facebook.react.bridge.WritableMap
import com.facebook.react.modules.core.DeviceEventManagerModule
Expand All @@ -9,6 +8,7 @@ import com.facebook.react.uimanager.UIManagerHelper
import com.facebook.react.uimanager.events.Event
import com.facebook.react.uimanager.events.EventDispatcher
import com.reactnativekeyboardcontroller.listeners.WindowDimensionListener
import com.reactnativekeyboardcontroller.log.Logger

fun ThemedReactContext.setupWindowDimensionsListener() {
WindowDimensionListener(this)
Expand All @@ -25,5 +25,5 @@ fun ThemedReactContext?.emitEvent(event: String, params: WritableMap) {
?.getJSModule(DeviceEventManagerModule.RCTDeviceEventEmitter::class.java)
?.emit(event, params)

Log.i("ThemedReactContext", event)
Logger.i("ThemedReactContext", event)
}
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,9 @@ package com.reactnativekeyboardcontroller.extensions

import android.graphics.Rect
import android.os.Build
import android.util.Log
import android.view.View
import androidx.annotation.RequiresApi
import com.reactnativekeyboardcontroller.log.Logger

/**
* Call this every time when using [ViewCompat.setOnApplyWindowInsetsListener]
Expand Down Expand Up @@ -43,7 +43,7 @@ fun View.copyBoundsInWindow(rect: Rect) {
getLocationInWindow(tmpIntArr)
rect.offset(tmpIntArr[0], tmpIntArr[1])
} else {
Log.w("View.copyBoundsInWindow", "Can not copy bounds as view is not attached to window")
Logger.w("View.copyBoundsInWindow", "Can not copy bounds as view is not attached to window")
}
}

Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
package com.reactnativekeyboardcontroller.listeners

import android.os.Build
import android.util.Log
import android.view.View
import android.view.ViewTreeObserver.OnGlobalFocusChangeListener
import androidx.core.graphics.Insets
Expand All @@ -21,6 +20,7 @@ import com.reactnativekeyboardcontroller.extensions.dp
import com.reactnativekeyboardcontroller.extensions.emitEvent
import com.reactnativekeyboardcontroller.extensions.isKeyboardAnimation
import com.reactnativekeyboardcontroller.interactive.InteractiveKeyboardProvider
import com.reactnativekeyboardcontroller.log.Logger
import kotlin.math.abs

private val TAG = KeyboardAnimationCallback::class.qualifiedName
Expand Down Expand Up @@ -137,7 +137,7 @@ class KeyboardAnimationCallback(
val isKeyboardSizeEqual = this.persistentKeyboardHeight == keyboardHeight

if (isKeyboardFullyVisible && !isKeyboardSizeEqual && !isResizeHandledInCallbackMethods) {
Log.i(TAG, "onApplyWindowInsets: ${this.persistentKeyboardHeight} -> $keyboardHeight")
Logger.i(TAG, "onApplyWindowInsets: ${this.persistentKeyboardHeight} -> $keyboardHeight")
layoutObserver?.syncUpLayout()
this.onKeyboardResized(keyboardHeight)
}
Expand Down Expand Up @@ -182,7 +182,7 @@ class KeyboardAnimationCallback(
getEventParams(keyboardHeight),
)

Log.i(TAG, "HEIGHT:: $keyboardHeight TAG:: $viewTagFocused")
Logger.i(TAG, "HEIGHT:: $keyboardHeight TAG:: $viewTagFocused")
context.dispatchEvent(
eventPropagationView.id,
KeyboardTransitionEvent(
Expand Down Expand Up @@ -229,9 +229,9 @@ class KeyboardAnimationCallback(
progress = abs((height / persistentKeyboardHeight)).let { if (it.isNaN()) 0.0 else it }
} catch (e: ArithmeticException) {
// do nothing, just log an exception send progress as 0
Log.w(TAG, "Caught arithmetic exception during `progress` calculation: $e")
Logger.w(TAG, "Caught arithmetic exception during `progress` calculation: $e")
}
Log.i(
Logger.i(
TAG,
"DiffY: $diffY $height $progress ${InteractiveKeyboardProvider.isInteractive} $viewTagFocused",
)
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
package com.reactnativekeyboardcontroller.log

import android.util.Log
import com.reactnativekeyboardcontroller.BuildConfig

object Logger {
private val enabled = BuildConfig.DEBUG

fun i(tag: String?, message: String, throwable: Throwable? = null) {
if (enabled) {
Log.i(tag, message, throwable)
}
}

fun w(tag: String?, message: String, throwable: Throwable? = null) {
if (enabled) {
Log.w(tag, message, throwable)
}
}
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
package com.reactnativekeyboardcontroller.modal

import android.util.Log
import android.view.WindowManager
import androidx.core.view.ViewCompat
import com.facebook.react.uimanager.ThemedReactContext
Expand All @@ -13,6 +12,7 @@ import com.facebook.react.views.view.ReactViewGroup
import com.reactnativekeyboardcontroller.BuildConfig
import com.reactnativekeyboardcontroller.listeners.KeyboardAnimationCallback
import com.reactnativekeyboardcontroller.listeners.KeyboardAnimationCallbackConfig
import com.reactnativekeyboardcontroller.log.Logger

private val TAG = ModalAttachedWatcher::class.qualifiedName

Expand All @@ -33,7 +33,7 @@ class ModalAttachedWatcher(
val modal = try {
uiManager?.resolveView(event.viewTag) as? ReactModalHostView
} catch (ignore: Exception) {
Log.w(TAG, "Can not resolve view for Modal#${event.viewTag}", ignore)
Logger.w(TAG, "Can not resolve view for Modal#${event.viewTag}", ignore)
null
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,13 +3,13 @@ package com.reactnativekeyboardcontroller.modules
import android.animation.ArgbEvaluator
import android.animation.ValueAnimator
import android.os.Build
import android.util.Log
import androidx.annotation.RequiresApi
import androidx.core.view.WindowInsetsCompat
import androidx.core.view.WindowInsetsControllerCompat
import com.facebook.react.bridge.ReactApplicationContext
import com.facebook.react.bridge.UiThreadUtil
import com.reactnativekeyboardcontroller.extensions.rootView
import com.reactnativekeyboardcontroller.log.Logger
import com.reactnativekeyboardcontroller.views.EdgeToEdgeReactViewGroup

private val TAG = StatusBarManagerCompatModuleImpl::class.qualifiedName
Expand All @@ -31,7 +31,7 @@ class StatusBarManagerCompatModuleImpl(private val mReactContext: ReactApplicati
fun setColor(color: Int, animated: Boolean) {
val activity = mReactContext.currentActivity
if (activity == null) {
Log.w(TAG, "StatusBarManagerCompatModule: Ignored status bar change, current activity is null.")
Logger.w(TAG, "StatusBarManagerCompatModule: Ignored status bar change, current activity is null.")
return
}

Expand Down Expand Up @@ -69,7 +69,7 @@ class StatusBarManagerCompatModuleImpl(private val mReactContext: ReactApplicati
if (this.controller == null) {
val activity = mReactContext.currentActivity
if (activity == null) {
Log.w(
Logger.w(
TAG,
"StatusBarManagerCompatModule: can not get `WindowInsetsControllerCompat` because current activity is null.",
)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,6 @@ import android.annotation.SuppressLint
import android.content.res.Configuration
import android.os.Handler
import android.os.Looper
import android.util.Log
import android.widget.FrameLayout
import androidx.core.view.ViewCompat
import androidx.core.view.WindowCompat
Expand All @@ -19,6 +18,7 @@ import com.reactnativekeyboardcontroller.extensions.rootView
import com.reactnativekeyboardcontroller.extensions.setupWindowDimensionsListener
import com.reactnativekeyboardcontroller.listeners.KeyboardAnimationCallback
import com.reactnativekeyboardcontroller.listeners.KeyboardAnimationCallbackConfig
import com.reactnativekeyboardcontroller.log.Logger
import com.reactnativekeyboardcontroller.modal.ModalAttachedWatcher

private val TAG = EdgeToEdgeReactViewGroup::class.qualifiedName
Expand Down Expand Up @@ -149,7 +149,7 @@ class EdgeToEdgeReactViewGroup(private val reactContext: ThemedReactContext) : R
it.requestApplyInsetsWhenAttached()
}
} else {
Log.w(TAG, "Can not setup keyboard animation listener, since `currentActivity` is null")
Logger.w(TAG, "Can not setup keyboard animation listener, since `currentActivity` is null")
}
}

Expand Down

0 comments on commit 7c9c450

Please sign in to comment.