Skip to content

Commit

Permalink
Make MouseEvent.nativeEvent and KeyEvent.nativeKeyEvent as Any?, move…
Browse files Browse the repository at this point in the history
… desktop code to skikoMain

Also introduce extensions, which should be used by the users, if they need interop with AWT:
val PointerEvent.awtEventOrNull: java.awt.event.MouseEvent?
val KeyEvent.awtEventOrNull: java.awt.event.KeyEvent?

We gradually get rid of AWT from Compose core codebase, AWT will be just one of the implementations.

Backward compatibility isn't violated, this change was before Compose MPP 1.0

PointerEvent.awtEvent, KeyEvent.awtEvent are deprecated, because we shipped them in 1.0 without Experimental annotation

Also, this CL contains small fix for JetBrains/compose-multiplatform#1457 in KeyEvent.desktop.kt file
If Caps is on, or it is not English layout, Linux sends LOCATION_UNKNOWN instead of LOCATION_STANDARD

Change-Id: I929d5d854e15f59d1dcddd6dc85221253c57a684
Test: ./gradlew jvmTest desktopTest -Pandroidx.compose.multiplatformEnabled=true
  • Loading branch information
igordmn authored and Oleksandr Karpovich committed Oct 26, 2022
1 parent 7713197 commit 9a316bf
Show file tree
Hide file tree
Showing 13 changed files with 147 additions and 112 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -16,14 +16,16 @@

package androidx.compose.foundation.gestures

import androidx.compose.runtime.Composable
import androidx.compose.foundation.fastFold
import androidx.compose.foundation.DesktopPlatform
import androidx.compose.foundation.fastFold
import androidx.compose.runtime.Composable
import androidx.compose.runtime.compositionLocalOf
import androidx.compose.ui.unit.Density
import androidx.compose.ui.unit.IntSize
import androidx.compose.ui.ExperimentalComposeUiApi
import androidx.compose.ui.awt.awtEventOrNull
import androidx.compose.ui.geometry.Offset
import androidx.compose.ui.input.pointer.PointerEvent
import androidx.compose.ui.unit.Density
import androidx.compose.ui.unit.IntSize
import androidx.compose.ui.unit.dp
import java.awt.event.MouseWheelEvent
import kotlin.math.sqrt
Expand Down Expand Up @@ -96,11 +98,11 @@ private fun calculateOffsetByPage(event: PointerEvent, bounds: IntSize): Offset

private val PointerEvent.scrollAmount
get() =
(mouseEvent as? MouseWheelEvent)?.scrollAmount?.toFloat() ?: 1f
(awtEventOrNull as? MouseWheelEvent)?.scrollAmount?.toFloat() ?: 1f

private val PointerEvent.shouldScrollByPage
get() =
(mouseEvent as? MouseWheelEvent)?.scrollType == MouseWheelEvent.WHEEL_BLOCK_SCROLL
(awtEventOrNull as? MouseWheelEvent)?.scrollType == MouseWheelEvent.WHEEL_BLOCK_SCROLL

private val PointerEvent.totalScrollDelta
get() = this.changes.fastFold(Offset.Zero) { acc, c -> acc + c.scrollDelta }
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@

package androidx.compose.foundation.text

import androidx.compose.ui.awt.awtEventOrNull
import androidx.compose.ui.input.key.KeyEvent

private fun Char.isPrintable(): Boolean {
Expand All @@ -27,5 +28,5 @@ private fun Char.isPrintable(): Boolean {
}

actual val KeyEvent.isTypedEvent: Boolean
get() = nativeKeyEvent.id == java.awt.event.KeyEvent.KEY_TYPED &&
nativeKeyEvent.keyChar.isPrintable()
get() = awtEventOrNull?.id == java.awt.event.KeyEvent.KEY_TYPED &&
awtEventOrNull?.keyChar?.isPrintable() == true
Original file line number Diff line number Diff line change
Expand Up @@ -17,10 +17,11 @@
package androidx.compose.foundation.text.selection

import androidx.compose.ui.Modifier
import androidx.compose.ui.awt.awtEventOrNull
import androidx.compose.ui.input.pointer.PointerEvent

internal actual val PointerEvent.isShiftPressed: Boolean
get() = mouseEvent?.isShiftDown ?: false
get() = awtEventOrNull?.isShiftDown ?: false

/**
* Magnification is not supported on desktop.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,20 +15,11 @@
*/
package androidx.compose.ui

import androidx.compose.ui.geometry.Offset
import androidx.compose.ui.input.pointer.PointerButtons
import androidx.compose.ui.input.pointer.PointerEventType
import androidx.compose.ui.input.pointer.PointerId
import androidx.compose.ui.input.pointer.PointerInputEvent
import androidx.compose.ui.input.pointer.PointerInputEventData
import androidx.compose.ui.input.pointer.PointerKeyboardModifiers
import androidx.compose.ui.input.pointer.PointerType
import androidx.compose.ui.platform.AccessibilityController
import androidx.compose.ui.platform.AccessibilityControllerImpl
import androidx.compose.ui.platform.PlatformComponent
import androidx.compose.ui.platform.SkiaBasedOwner
import java.awt.event.InputMethodEvent
import java.awt.event.MouseEvent

internal actual fun ComposeScene.onPlatformInputMethodEvent(event: Any) {
require(event is InputMethodEvent)
Expand All @@ -46,49 +37,6 @@ internal actual fun ComposeScene.onPlatformInputMethodEvent(event: Any) {
}
}

internal actual fun pointerInputEvent(
eventType: PointerEventType,
position: Offset,
timeMillis: Long,
nativeEvent: Any?,
type: PointerType,
isMousePressed: Boolean,
pointerId: Long,
scrollDelta: Offset,
buttons: PointerButtons,
keyboardModifiers: PointerKeyboardModifiers,
): PointerInputEvent {
return PointerInputEvent(
eventType,
timeMillis,
listOf(
PointerInputEventData(
PointerId(pointerId),
timeMillis,
position,
position,
isMousePressed,
pressure = 1.0f,
type,
scrollDelta = scrollDelta
)
),
buttons,
keyboardModifiers,
nativeEvent as MouseEvent?
)
}

@OptIn(ExperimentalComposeUiApi::class)
internal actual val DefaultPointerButtons: PointerButtons = PointerButtons()

@OptIn(ExperimentalComposeUiApi::class)
internal actual val DefaultPointerKeyboardModifiers: PointerKeyboardModifiers =
PointerKeyboardModifiers()

@OptIn(ExperimentalComposeUiApi::class)
internal actual val PrimaryPressedPointerButtons: PointerButtons =
PointerButtons(isPrimaryPressed = true)
internal actual fun makeAccessibilityController(
skiaBasedOwner: SkiaBasedOwner,
component: PlatformComponent
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,59 @@
package androidx.compose.ui.awt

import androidx.compose.ui.input.key.KeyEvent
import androidx.compose.ui.input.pointer.PointerEvent

/**
* The original raw native event from AWT
*/
@Deprecated(
"Use awtEventOrNull. `awtEvent` will be removed in Compose 1.3",
replaceWith = ReplaceWith("awtEventOrNull")
)
val PointerEvent.awtEvent: java.awt.event.MouseEvent get() {
require(nativeEvent is java.awt.event.MouseEvent) {
"nativeEvent wasn't sent by AWT. Make sure, that you use AWT backed API" +
" (from androidx.compose.ui.awt.* or from androidx.compose.ui.window.*)"
}
return nativeEvent
}

/**
* The original raw native event from AWT
*/
@Deprecated(
"Use awtEventOrNull. `awtEvent` will be removed in Compose 1.3",
replaceWith = ReplaceWith("awtEventOrNull")
)
val KeyEvent.awtEvent: java.awt.event.KeyEvent get() {
require(nativeKeyEvent is java.awt.event.KeyEvent) {
"nativeKeyEvent wasn't sent by AWT. Make sure, that you use AWT backed API" +
" (from androidx.compose.ui.awt.* or from androidx.compose.ui.window.*)"
}
return nativeKeyEvent
}

/**
* The original raw native event from AWT.
*
* Null if:
* - the native event is sent by another framework (when Compose UI is embed into it)
* - there no native event (in tests, for example)
* - there was a synthetic move event sent by compose on relayout
* - there was a synthetic move event sent by compose when move is missing between two non-move events
*/
@Suppress("DEPRECATION")
val PointerEvent.awtEventOrNull: java.awt.event.MouseEvent? get() {
return nativeEvent as? java.awt.event.MouseEvent
}

/**
* The original raw native event from AWT.
*
* Null if:
* - the native event is sent by another framework (when Compose UI is embed into it)
* - there no native event (in tests, for example)
*/
val KeyEvent.awtEventOrNull: java.awt.event.KeyEvent? get() {
return nativeKeyEvent as? java.awt.event.KeyEvent
}
Original file line number Diff line number Diff line change
Expand Up @@ -16,19 +16,29 @@

package androidx.compose.ui.input.key

import androidx.compose.ui.awt.awtEventOrNull
import java.awt.event.KeyEvent.KEY_LOCATION_STANDARD
import java.awt.event.KeyEvent.KEY_LOCATION_UNKNOWN
import java.awt.event.KeyEvent.KEY_PRESSED
import java.awt.event.KeyEvent.KEY_RELEASED
import java.awt.event.KeyEvent.VK_UNDEFINED

/**
* The native desktop [KeyEvent][KeyEventAwt].
*/
actual typealias NativeKeyEvent = java.awt.event.KeyEvent
actual typealias NativeKeyEvent = Any

/**
* The key that was pressed.
*/
actual val KeyEvent.key: Key
get() = Key(nativeKeyEvent.keyCode, nativeKeyEvent.keyLocation)
get() = Key(
awtEventOrNull?.keyCode ?: VK_UNDEFINED,
awtEventOrNull?.keyLocationForCompose ?: KEY_LOCATION_STANDARD
)

private val java.awt.event.KeyEvent.keyLocationForCompose get() =
if (keyLocation == KEY_LOCATION_UNKNOWN) KEY_LOCATION_STANDARD else keyLocation

/**
* The UTF16 value corresponding to the key event that was pressed. The unicode character
Expand All @@ -47,13 +57,13 @@ actual val KeyEvent.key: Key
* second from the low-surrogates range (\uDC00-\uDFFF).
*/
actual val KeyEvent.utf16CodePoint: Int
get() = nativeKeyEvent.keyChar.code
get() = awtEventOrNull?.keyChar?.code ?: 0

/**
* The [type][KeyEventType] of key event.
*/
actual val KeyEvent.type: KeyEventType
get() = when (nativeKeyEvent.id) {
get() = when (awtEventOrNull?.id) {
KEY_PRESSED -> KeyEventType.KeyDown
KEY_RELEASED -> KeyEventType.KeyUp
else -> KeyEventType.Unknown
Expand All @@ -63,22 +73,22 @@ actual val KeyEvent.type: KeyEventType
* Indicates whether the Alt key is pressed.
*/
actual val KeyEvent.isAltPressed: Boolean
get() = nativeKeyEvent.isAltDown || nativeKeyEvent.isAltGraphDown
get() = awtEventOrNull?.isAltDown == true || awtEventOrNull?.isAltGraphDown == true

/**
* Indicates whether the Ctrl key is pressed.
*/
actual val KeyEvent.isCtrlPressed: Boolean
get() = nativeKeyEvent.isControlDown
get() = awtEventOrNull?.isControlDown == true

/**
* Indicates whether the Meta key is pressed.
*/
actual val KeyEvent.isMetaPressed: Boolean
get() = nativeKeyEvent.isMetaDown
get() = awtEventOrNull?.isMetaDown == true

/**
* Indicates whether the Shift key is pressed.
*/
actual val KeyEvent.isShiftPressed: Boolean
get() = nativeKeyEvent.isShiftDown
get() = awtEventOrNull?.isShiftDown == true
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ import java.awt.event.MouseWheelEvent
*/
@Deprecated(
"Use Modifier.pointerInput + PointerEventType.Scroll." +
"See the comment to mouseScrollFilter"
"See the comment to mouseScrollFilter. Will be removed in 1.3"
)
sealed class MouseScrollUnit {
/**
Expand All @@ -49,7 +49,7 @@ sealed class MouseScrollUnit {
*/
@Deprecated(
"Use Modifier.pointerInput + PointerEventType.Scroll." +
"See the comment to mouseScrollFilter"
"See the comment to mouseScrollFilter. Will be removed in 1.3"
)
data class Line(val value: Float) : MouseScrollUnit()

Expand All @@ -63,7 +63,7 @@ sealed class MouseScrollUnit {
*/
@Deprecated(
"Use Modifier.pointerInput + PointerEventType.Scroll." +
"See the comment to mouseScrollFilter"
"See the comment to mouseScrollFilter. Will be removed in 1.3"
)
data class Page(val value: Float) : MouseScrollUnit()
}
Expand All @@ -73,7 +73,7 @@ sealed class MouseScrollUnit {
*/
@Deprecated(
"Use Modifier.pointerInput + PointerEventType.Scroll." +
"See the comment to mouseScrollFilter"
"See the comment to mouseScrollFilter. Will be removed in 1.3"
)
class MouseScrollEvent(
/**
Expand Down Expand Up @@ -106,7 +106,7 @@ class MouseScrollEvent(
* false, the scroll event will be sent to this [mouseScrollFilter]'s parent.
*/
@Deprecated(
"Use Modifier.pointerInput + PointerEventType.Scroll",
"Use Modifier.pointerInput + PointerEventType.Scroll. Will be removed in 1.3",
replaceWith = ReplaceWith(
"pointerInput(Unit) { \n" +
" awaitPointerEventScope {\n" +
Expand Down Expand Up @@ -146,7 +146,7 @@ fun Modifier.mouseScrollFilter(
// the more proper behaviour would be to batch multiple scroll events into the single one
while (true) {
val event = awaitScrollEvent()
val mouseEvent = event.mouseEvent as? MouseWheelEvent
val mouseEvent = event.nativeEvent as? MouseWheelEvent
val mouseChange = event.changes.find { it.type == PointerType.Mouse }
if (mouseChange != null && !mouseChange.isConsumed) {
val legacyEvent = mouseEvent.toLegacyEvent(mouseChange.scrollDelta)
Expand Down Expand Up @@ -185,7 +185,7 @@ private fun MouseWheelEvent?.toLegacyEvent(scrollDelta: Offset): MouseScrollEven

@Deprecated(
"Use Modifier.pointerInput + PointerEventType.Scroll." +
"See the comment to mouseScrollFilter"
"See the comment to mouseScrollFilter. Will be removed in 1.3"
)
enum class MouseScrollOrientation {
Vertical, Horizontal
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@

package androidx.compose.ui.platform

import androidx.compose.ui.awt.awtEventOrNull
import androidx.compose.ui.input.key.KeyInputModifier
import androidx.compose.ui.input.key.KeyEvent
import androidx.compose.ui.input.key.KeyEventType
Expand All @@ -30,7 +31,7 @@ internal actual fun sendKeyEvent(
keyEvent: KeyEvent
): Boolean {
when {
keyEvent.nativeKeyEvent.id == java.awt.event.KeyEvent.KEY_TYPED ->
keyEvent.awtEventOrNull?.id == java.awt.event.KeyEvent.KEY_TYPED ->
platformInputService.charKeyPressed = true
keyEvent.type == KeyEventType.KeyUp ->
platformInputService.charKeyPressed = false
Expand Down
Loading

0 comments on commit 9a316bf

Please sign in to comment.