Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit ebfae185 authored by Jordan Silva's avatar Jordan Silva
Browse files

Refactoring OverviewCommandHelper (2/3)

This CL should not affect the behavior of OverviewCommandHelper.
- It splits executeCommand into smaller functions
- Rearrange public/private functions
- Adds extra logs.

Bug: 352046797
Bug: 351122926
Flag: EXEMPT bugfix.
Test: Manual.
Change-Id: I283f179794af812973a559db6291febe19e3c6d7
parent e7ae4e31
Loading
Loading
Loading
Loading
+135 −124
Original line number Diff line number Diff line
@@ -73,21 +73,33 @@ class OverviewCommandHelper(
    private val visibleRecentsView: RecentsView<*, *>?
        get() = activityInterface.getVisibleRecentsView<RecentsView<*, *>>()

    /** Called when the command finishes execution. */
    private fun onCommandFinished(command: CommandInfo) {
        command.status = CommandStatus.COMPLETED
        if (commandQueue.first() !== command) {
            Log.d(
                TAG,
                "next task not scheduled. First pending command type " +
                    "is ${commandQueue.first()} - command type is: $command"
            )
    /**
     * Adds a command to be executed next, after all pending tasks are completed. Max commands that
     * can be queued is [.MAX_QUEUE_SIZE]. Requests after reaching that limit will be silently
     * dropped.
     */
    @BinderThread
    fun addCommand(type: CommandType) {
        if (commandQueue.size >= MAX_QUEUE_SIZE) {
            Log.d(TAG, "commands queue is full ($commandQueue). command not added: $type")
            return
        }

        Log.d(TAG, "command executed successfully! $command")
        commandQueue.remove(command)
        executeNext()
        val command = CommandInfo(type)
        commandQueue.add(command)
        Log.d(TAG, "command added: $command")

        if (commandQueue.size == 1) {
            Executors.MAIN_EXECUTOR.execute { executeNext() }
        }
    }

    fun canStartHomeSafely(): Boolean = commandQueue.isEmpty() || commandQueue.first().type == HOME

    /** Clear pending commands from the queue */
    fun clearPendingCommands() {
        Log.d(TAG, "clearing pending commands: $commandQueue")
        commandQueue.clear()
    }

    /**
@@ -104,9 +116,10 @@ class OverviewCommandHelper(
                    return
                }

        command.status = CommandStatus.PROCESSING
        Log.d(TAG, "executing command: $command")
        val result = executeCommand(command)

        val result = executeCommand(command)
        Log.d(TAG, "command executed: $command with result: $result")
        if (result) {
            onCommandFinished(command)
@@ -116,42 +129,53 @@ class OverviewCommandHelper(
    }

    /**
     * Adds a command to be executed next, after all pending tasks are completed. Max commands that
     * can be queued is [.MAX_QUEUE_SIZE]. Requests after reaching that limit will be silently
     * dropped.
     * Executes the task and returns true if next task can be executed. If false, then the next task
     * is deferred until [.scheduleNextTask] is called
     */
    @BinderThread
    fun addCommand(type: CommandType) {
        if (commandQueue.size >= MAX_QUEUE_SIZE) {
            Log.d(TAG, "commands queue is full ($commandQueue). command not added: $type")
            return
    private fun executeCommand(command: CommandInfo): Boolean {
        if (waitForToggleCommandComplete && command.type == TOGGLE) {
            Log.d(TAG, "executeCommand: $command - waiting for toggle command complete")
            return true
        }

        val command = CommandInfo(type)
        commandQueue.add(command)
        Log.d(TAG, "command added: $command")

        if (commandQueue.size == 1) {
            Executors.MAIN_EXECUTOR.execute { executeNext() }
        val recentsView = visibleRecentsView
        Log.d(TAG, "executeCommand: $command - visibleRecentsView: $recentsView")
        return if (recentsView != null) {
            executeWhenRecentsIsVisible(command, recentsView)
        } else {
            executeWhenRecentsIsNotVisible(command)
        }
    }

    fun canStartHomeSafely(): Boolean = commandQueue.isEmpty() || commandQueue.first().type == HOME

    /** Clear commands from the queue */
    fun clearPendingCommands() {
        Log.d(TAG, "clearing pending commands: $commandQueue")
        commandQueue.clear()
    private fun executeWhenRecentsIsVisible(
        command: CommandInfo,
        recentsView: RecentsView<*, *>,
    ): Boolean =
        when (command.type) {
            SHOW -> true // already visible
            KEYBOARD_INPUT,
            HIDE -> {
                if (recentsView.isHandlingTouch) {
                    true
                } else {
                    keyboardTaskFocusIndex = PagedView.INVALID_PAGE
                    val currentPage = recentsView.nextPage
                    val taskView = recentsView.getTaskViewAt(currentPage)
                    launchTask(recentsView, taskView, command)
                }

    private fun getNextTask(view: RecentsView<*, *>): TaskView? {
        val runningTaskView = view.runningTaskView

        return if (runningTaskView == null) {
            view.getTaskViewAt(0)
            }
            TOGGLE -> {
                val taskView =
                    if (recentsView.runningTaskView == null) {
                        recentsView.getTaskViewAt(0)
                    } else {
            val nextTask = view.nextTaskView
            nextTask ?: runningTaskView
                        recentsView.nextTaskView ?: recentsView.runningTaskView
                    }
                launchTask(recentsView, taskView, command)
            }
            HOME -> {
                recentsView.startHome()
                true
            }
        }

@@ -182,24 +206,10 @@ class OverviewCommandHelper(
        }
    }

    /**
     * Executes the task and returns true if next task can be executed. If false, then the next task
     * is deferred until [.scheduleNextTask] is called
     */
    private fun executeCommand(command: CommandInfo): Boolean {
        command.status = CommandStatus.PROCESSING

        if (waitForToggleCommandComplete && command.type == TOGGLE) {
            Log.d(TAG, "executeCommand: $command - waiting for toggle command complete")
            return true
        }

        var recentsView = visibleRecentsView
        Log.d(TAG, "executeCommand: $command - visibleRecentsView: $recentsView")
        if (recentsView == null) {
            val activity = activityInterface.getCreatedContainer() as? RecentsViewContainer
            recentsView = activity?.getOverviewPanel()
            val deviceProfile = activity?.getDeviceProfile()
    private fun executeWhenRecentsIsNotVisible(command: CommandInfo): Boolean {
        val recentsViewContainer = activityInterface.getCreatedContainer() as? RecentsViewContainer
        val recentsView: RecentsView<*, *>? = recentsViewContainer?.getOverviewPanel()
        val deviceProfile = recentsViewContainer?.getDeviceProfile()
        val uiController = activityInterface.getTaskbarController()
        val allowQuickSwitch =
            FeatureFlags.ENABLE_KEYBOARD_QUICK_SWITCH.get() &&
@@ -237,33 +247,13 @@ class OverviewCommandHelper(
                keyboardTaskFocusIndex = 0
            TOGGLE -> {}
        }
        } else {
            return when (command.type) {
                SHOW -> true // already visible
                KEYBOARD_INPUT,
                HIDE -> {
                    if (recentsView.isHandlingTouch) {
                        true
                    } else {
                        keyboardTaskFocusIndex = PagedView.INVALID_PAGE
                        val currentPage = recentsView.nextPage
                        val taskView = recentsView.getTaskViewAt(currentPage)
                        launchTask(recentsView, taskView, command)
                    }
                }
                TOGGLE -> launchTask(recentsView, getNextTask(recentsView), command)
                HOME -> {
                    recentsView.startHome()
                    true
                }
            }
        }

        recentsView?.setKeyboardTaskFocusIndex(keyboardTaskFocusIndex)
        // Handle recents view focus when launching from home
        val animatorListener: Animator.AnimatorListener =
            object : AnimatorListenerAdapter() {
                override fun onAnimationStart(animation: Animator) {
                    Log.d(TAG, "switching to Overview state - onAnimationStart: $command")
                    super.onAnimationStart(animation)
                    updateRecentsViewFocus(command)
                    logShowOverviewFrom(command.type)
@@ -309,9 +299,11 @@ class OverviewCommandHelper(
                    controller: RecentsAnimationController,
                    targets: RecentsAnimationTargets
                ) {
                    Log.d(TAG, "recents animation started: $command")
                    updateRecentsViewFocus(command)
                    logShowOverviewFrom(command.type)
                    activityInterface.runOnInitBackgroundStateUI {
                        Log.d(TAG, "recents animation started - onInitBackgroundStateUI: $command")
                        interactionHandler.onGestureEnded(0f, PointF())
                    }
                    command.removeListener(this)
@@ -320,6 +312,7 @@ class OverviewCommandHelper(
                override fun onRecentsAnimationCanceled(
                    thumbnailDatas: HashMap<Int, ThumbnailData>
                ) {
                    Log.d(TAG, "recents animation canceled: $command")
                    interactionHandler.onGestureCancelled()
                    command.removeListener(this)

@@ -366,6 +359,23 @@ class OverviewCommandHelper(
        onCommandFinished(command)
    }

    /** Called when the command finishes execution. */
    private fun onCommandFinished(command: CommandInfo) {
        command.status = CommandStatus.COMPLETED
        if (commandQueue.first() !== command) {
            Log.d(
                TAG,
                "next task not scheduled. First pending command type " +
                    "is ${commandQueue.first()} - command type is: $command"
            )
            return
        }

        Log.d(TAG, "command executed successfully! $command")
        commandQueue.remove(command)
        executeNext()
    }

    private fun updateRecentsViewFocus(command: CommandInfo) {
        val recentsView: RecentsView<*, *> = visibleRecentsView ?: return
        if (command.type != KEYBOARD_INPUT && command.type != HIDE && command.type != SHOW) {
@@ -380,10 +390,11 @@ class OverviewCommandHelper(
        // here we launch overview with live tile.
        recentsView.viewRootImpl.touchModeChanged(false)
        // Ensure that recents view has focus so that it receives the followup key inputs
        if (requestFocus(recentsView.getTaskViewAt(keyboardTaskFocusIndex))) return
        if (requestFocus(recentsView.nextTaskView)) return
        if (requestFocus(recentsView.getTaskViewAt(0))) return
        requestFocus(recentsView)
        // Stops requesting focused after first view gets focused.
        recentsView.getTaskViewAt(keyboardTaskFocusIndex).requestFocus() ||
            recentsView.nextTaskView.requestFocus() ||
            recentsView.getTaskViewAt(0).requestFocus() ||
            recentsView.requestFocus()
    }

    private fun onRecentsViewFocusUpdated(command: CommandInfo) {
@@ -396,11 +407,11 @@ class OverviewCommandHelper(
        keyboardTaskFocusIndex = PagedView.INVALID_PAGE
    }

    private fun requestFocus(taskView: View?): Boolean {
        if (taskView == null) return false
        taskView.post {
            taskView.requestFocus()
            taskView.requestAccessibilityFocus()
    private fun View?.requestFocus(): Boolean {
        if (this == null) return false
        post {
            requestFocus()
            requestAccessibilityFocus()
        }
        return true
    }