Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@

package com.maddyhome.idea.vim.extension.hints

import com.intellij.openapi.editor.impl.EditorComponentImpl
import com.intellij.openapi.wm.impl.status.TextPanel
import com.intellij.ui.treeStructure.Tree
import java.awt.Component
import java.awt.Point
Expand Down Expand Up @@ -73,11 +75,16 @@ private fun collectTargets(
val location = location + (accessible.location ?: return)

accessible.size?.let { size ->
if (accessible.isShowing && (component.isClickable() || component is Tree)) {
if (accessible.isShowing && (component.isClickable() || component is Tree || component is TextPanel)) {
targets[component].let {
// For some reason, the same component may appear multiple times in the accessible tree.
if (it == null || it.depth > depth) {
targets[component] = HintTarget(component, location, size, depth)
targets[component] = HintTarget(component, location, size, depth).apply {
action = when (component) {
is Tree, is EditorComponentImpl -> ({ component.requestFocusInWindow() })
else -> HintTarget::clickCenter
}
}
}
}
}
Expand Down
19 changes: 19 additions & 0 deletions src/main/java/com/maddyhome/idea/vim/extension/hints/HintTarget.kt
Original file line number Diff line number Diff line change
Expand Up @@ -11,10 +11,29 @@ package com.maddyhome.idea.vim.extension.hints
import java.awt.Dimension
import java.awt.Point
import java.awt.Rectangle
import java.awt.Robot
import java.awt.event.InputEvent
import javax.accessibility.Accessible

internal data class HintTarget(val component: Accessible, val location: Point, val size: Dimension, val depth: Int) {
var hint: String = ""

val bounds: Rectangle get() = Rectangle(location, size)

/**
* The action to execute when the hint is selected.
*
* @return `true` if the action succeeded, `false` otherwise
*/
var action: Function1<HintTarget, Boolean> = { false }
fun action() = action(this)

fun clickCenter(): Boolean {
val robot = Robot()
val locationOnScreen = component.accessibleContext?.accessibleComponent?.locationOnScreen ?: return false
robot.mouseMove(locationOnScreen.x + bounds.width / 2, locationOnScreen.y + bounds.height / 2)
robot.mousePress(InputEvent.BUTTON1_DOWN_MASK)
robot.mouseRelease(InputEvent.BUTTON1_DOWN_MASK)
return true
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -78,9 +78,7 @@ class ToggleHintsAction : DumbAwareToggleAction() {
ShortcutDispatcher("hints", targets.associateBy { it.hint.lowercase() }, { target ->
popup.closeOk(null)
alarm.cancelAllRequests()
target.component.accessibleContext?.apply {
if (accessibleAction?.doAccessibleAction(0) == null && !accessibleComponent.isFocusTraversable) return@apply
accessibleComponent.requestFocus()
if (target.action()) {
highlight.setTarget(target)
alarm.addRequest({ highlight.setTarget(null) }, highlightDuration)
}
Expand Down
Loading