background

Record the iteration line caused by a P0 accident on an input method application line.

  1. Iteration 1

There is an operation popover on the keyboard. Close the popover when the keyboard is retracted. The code is as follows:

fun Activity.showExampleDialog(view: View) {
    AppCompatDialog(this).apply {
        setContentView(
            Button(this@showExampleDialog).apply {
                setOnClickListener {
                    dismiss()
                }
            }
        )
    }.show();
}
Copy the code
  1. In iteration 2, it is possible to perform some time-consuming operations when the keyboard is folded up, and if there are time-consuming operations, they are put into child threads for execution
    Executors.newSingleThreadExecutor().execute(Runnable {
    // Possible time-consuming operations
        dismiss()
    });
Copy the code
  1. Some suspicious crashes were found on iteration 3 lines. Given that the keyboard has been put away, the RD assessment has little impact. Put the entire callback block try directly inside.
Executors. NewSingleThreadExecutor (). The execute (Runnable {try {/ / may dismiss time-consuming operation ()} the catch (e: Exception) {}});Copy the code
  1. Iteration 4 changed Dialog to PopupWindow ‘as required.
fun Activity.showExamplePopWindow(view: View) {
    PopupWindow(this).apply {
        setContentView(
            Button(this@showExamplePopWindow).apply {
                setOnClickListener {
                    Executors.newSingleThreadExecutor().execute(Runnable {

                        try {
                            dismiss()
                        } catch (e: Exception) {
                        }
                    });
                }
            }
        )
    }.showAsDropDown(view);
}
Copy the code
  1. The accident

The popup window of this requirement is rarely used at ordinary times. It was useless for several months after the revision of the appeal. Suddenly one day, a popup window of operation was pushed, and after the push, a large number of online users gave feedback:

There is a popover on the keyboard that cannot be closed because it blocks the keyboard and the keyboard cannot be typed.Copy the code

(PS: Most users do not know how to kill the input method, the application does not do the bottom, also lost the opportunity to save themselves)

why

  1. Dialog’s dismiss method system has been used to determine the thread. If used in child threads, the system automatically cuts back to the main thread, but PopupWindow does not.
  2. After several iterations, the code deconstruction has changed, the code executing the dismiss function has been placed in another class, and the execution thread has been switched to a child thread.

To improve the

For programmers, among other things:

  1. Rough try… Cutting child threads can only solve the problem of the moment. Some problems are handled in a way that is not clear enough to cause more serious consequences than crashes.
  2. When changing the code, be sure to find a former to ask the background of the requirements and help review them
  3. Do callback methods that support execution by specified threads.
fun android.view.View.onClick(
    context: CoroutineContext = Dispatchers.Main,
    handler: suspend CoroutineScope. (v: android.view.View?). ->Unit
){ setOnClickListener { v -> CoroutineScope(context).launch { v? .let { handler(it) } } } }Copy the code

conclusion

Use this extension to familiarize yourself with Kotlin’s syntax

Compare the Java implementation to the simplicity of Koltin code.