From c143526e1c4a56134a397701dc384db3a6b7cfe7 Mon Sep 17 00:00:00 2001 From: Pierre-Yves Ricau Date: Sat, 27 Jul 2024 00:08:07 +0200 Subject: [PATCH] Add support for custom startInteraction start input events --- .../main/java/papa/InteractionOverlayView.kt | 2 +- papa/api/papa.api | 21 ++++++++++++------- papa/src/main/java/papa/InputTracker.kt | 5 ++++- .../main/java/papa/InteractionRuleClient.kt | 20 +++++++++++------- .../main/java/papa/InteractionStartInput.kt | 7 +++++++ 5 files changed, 38 insertions(+), 17 deletions(-) create mode 100644 papa/src/main/java/papa/InteractionStartInput.kt diff --git a/papa-dev/src/main/java/papa/InteractionOverlayView.kt b/papa-dev/src/main/java/papa/InteractionOverlayView.kt index 75d98b6..27b5bf7 100644 --- a/papa-dev/src/main/java/papa/InteractionOverlayView.kt +++ b/papa-dev/src/main/java/papa/InteractionOverlayView.kt @@ -69,7 +69,7 @@ class InteractionOverlayView( val interactionLines = trackedInteractionsWithFrameCount.map { (trackedInteraction, frameCount) -> val input = trackedInteraction.interactionInput?.let { deliveredInput -> - when (val inputEvent = deliveredInput.event) { + when (val inputEvent = (deliveredInput as DeliveredInput<*>).event) { is MotionEvent -> MotionEvent.actionToString(inputEvent.action) is KeyEvent -> KeyEvent.keyCodeToString(inputEvent.keyCode) else -> error("Unknown input event class ${inputEvent::class.java.name}") diff --git a/papa/api/papa.api b/papa/api/papa.api index 16ce3c5..c5f7021 100644 --- a/papa/api/papa.api +++ b/papa/api/papa.api @@ -201,12 +201,13 @@ public final class papa/AppVisibilityState : java/lang/Enum { public static fun values ()[Lpapa/AppVisibilityState; } -public final class papa/DeliveredInput { +public final class papa/DeliveredInput : papa/InteractionStartInput { public synthetic fun (Landroid/view/InputEvent;JJILkotlin/jvm/functions/Function0;Lkotlin/jvm/internal/DefaultConstructorMarker;)V public final fun getDeliveryUptime-UwyO8pc ()J public final fun getEvent ()Landroid/view/InputEvent; public final fun getEventUptime-UwyO8pc ()J public final fun getFramesSinceDelivery ()I + public fun getInputUptime-UwyO8pc ()J public final fun takeOverTraceEnd ()Lkotlin/jvm/functions/Function0; public fun toString ()Ljava/lang/String; } @@ -237,7 +238,7 @@ public abstract interface class papa/InteractionEventSink { public abstract class papa/InteractionResult : papa/InteractionResultData { public synthetic fun (Lpapa/InteractionResultData;Lkotlin/jvm/internal/DefaultConstructorMarker;)V - public fun getInteractionInput ()Lpapa/DeliveredInput; + public fun getInteractionInput ()Lpapa/InteractionStartInput; public fun getRunningFrameCount ()I public fun getSentEvents ()Ljava/util/List; public fun toString ()Ljava/lang/String; @@ -257,14 +258,14 @@ public final class papa/InteractionResult$Finished : papa/InteractionResult { } public abstract interface class papa/InteractionResultData { - public abstract fun getInteractionInput ()Lpapa/DeliveredInput; + public abstract fun getInteractionInput ()Lpapa/InteractionStartInput; public abstract fun getRunningFrameCount ()I public abstract fun getSentEvents ()Ljava/util/List; } public final class papa/InteractionResultDataPayload : papa/InteractionResultData { - public fun (Lpapa/DeliveredInput;ILjava/util/List;)V - public fun getInteractionInput ()Lpapa/DeliveredInput; + public fun (Lpapa/InteractionStartInput;ILjava/util/List;)V + public fun getInteractionInput ()Lpapa/InteractionStartInput; public fun getRunningFrameCount ()I public fun getSentEvents ()Ljava/util/List; } @@ -289,6 +290,10 @@ public final class papa/InteractionScope { public final fun getOnEventCallbacks ()Ljava/util/List; } +public abstract interface class papa/InteractionStartInput { + public abstract fun getInputUptime-UwyO8pc ()J +} + public abstract interface class papa/InteractionTrace { public static final field Companion Lpapa/InteractionTrace$Companion; public abstract fun endTrace ()V @@ -307,7 +312,7 @@ public abstract interface class papa/OnEventScope { public abstract fun getInteractionInput ()Lpapa/DeliveredInput; public abstract fun recordSingleFrameInteraction (Lpapa/InteractionTrace;)Lpapa/FinishingInteraction; public abstract fun runningInteractions ()Ljava/util/List; - public abstract fun startInteraction-HG0u8IE (Lpapa/InteractionTrace;J)Lpapa/RunningInteraction; + public abstract fun startInteraction-SxA4cEA (Lpapa/InteractionStartInput;Lpapa/InteractionTrace;J)Lpapa/RunningInteraction; } public final class papa/OnEventScope$DefaultImpls { @@ -316,7 +321,7 @@ public final class papa/OnEventScope$DefaultImpls { public static synthetic fun cancelRunningInteractions$default (Lpapa/OnEventScope;Ljava/lang/String;ILjava/lang/Object;)V public static fun recordSingleFrameInteraction (Lpapa/OnEventScope;Lpapa/InteractionTrace;)Lpapa/FinishingInteraction; public static synthetic fun recordSingleFrameInteraction$default (Lpapa/OnEventScope;Lpapa/InteractionTrace;ILjava/lang/Object;)Lpapa/FinishingInteraction; - public static synthetic fun startInteraction-HG0u8IE$default (Lpapa/OnEventScope;Lpapa/InteractionTrace;JILjava/lang/Object;)Lpapa/RunningInteraction; + public static synthetic fun startInteraction-SxA4cEA$default (Lpapa/OnEventScope;Lpapa/InteractionStartInput;Lpapa/InteractionTrace;JILjava/lang/Object;)Lpapa/RunningInteraction; } public abstract class papa/PapaEvent { @@ -431,7 +436,7 @@ public final class papa/SentEvent { } public abstract interface class papa/TrackedInteraction { - public abstract fun getInteractionInput ()Lpapa/DeliveredInput; + public abstract fun getInteractionInput ()Lpapa/InteractionStartInput; public abstract fun getSentEvents ()Ljava/util/List; public abstract fun recordEvent ()V } diff --git a/papa/src/main/java/papa/InputTracker.kt b/papa/src/main/java/papa/InputTracker.kt index f607a56..6faa84c 100644 --- a/papa/src/main/java/papa/InputTracker.kt +++ b/papa/src/main/java/papa/InputTracker.kt @@ -45,7 +45,7 @@ class DeliveredInput( val eventUptime: Duration, val framesSinceDelivery: Int, private var endTrace: (() -> Unit)? -) { +) : InteractionStartInput { fun takeOverTraceEnd(): (() -> Unit)? { val transferedEndTrace = endTrace @@ -65,6 +65,9 @@ class DeliveredInput( return copy } + override val inputUptime: Duration + get() = eventUptime + override fun toString(): String { return "DeliveredInput(" + "deliveryUptime=${deliveryUptime.toString(MILLISECONDS)}, " + diff --git a/papa/src/main/java/papa/InteractionRuleClient.kt b/papa/src/main/java/papa/InteractionRuleClient.kt index 2979cbb..eba8980 100644 --- a/papa/src/main/java/papa/InteractionRuleClient.kt +++ b/papa/src/main/java/papa/InteractionRuleClient.kt @@ -109,7 +109,7 @@ private class InteractionEngine( private var eventInScope: SentEvent? = null inner class RealRunningInteraction( - override val interactionInput: DeliveredInput?, + override val interactionInput: InteractionStartInput?, private val trace: InteractionTrace, cancelTimeout: Duration ) : RunningInteraction, FinishingInteraction, FrameCallback { @@ -224,13 +224,17 @@ private class InteractionEngine( override val interactionInput = interactionInput override fun startInteraction( + interactionStartInput: InteractionStartInput?, trace: InteractionTrace, cancelTimeout: Duration, ): RunningInteraction { // If the interaction input trace end isn't taken over yet, end it. interactionInput?.takeOverTraceEnd()?.invoke() + val runningInteraction = RealRunningInteraction( - interactionInput = interactionInput, + // Default to custom interactionStartInput if passed in, otherwise default to delivered + // input (key or tap) + interactionInput = interactionStartInput ?: interactionInput, trace = trace, cancelTimeout ) @@ -265,6 +269,7 @@ interface OnEventScope { val event: EventType fun startInteraction( + interactionStartInput: InteractionStartInput? = null, trace: InteractionTrace = InteractionTrace.fromInputDelivered(event, interactionInput), cancelTimeout: Duration = 1.minutes, ): RunningInteraction @@ -277,7 +282,7 @@ interface OnEventScope { fun recordSingleFrameInteraction( trace: InteractionTrace = InteractionTrace.fromInputDelivered(event, interactionInput), ): FinishingInteraction { - return startInteraction(trace).finish() + return startInteraction(trace = trace).finish() } /** @@ -334,7 +339,7 @@ fun interface InteractionTrace { interface TrackedInteraction { val sentEvents: List> - val interactionInput: DeliveredInput? + val interactionInput: InteractionStartInput? /** * Adds the current event instance to the list of events (if not already added). @@ -356,7 +361,7 @@ interface InteractionResultData { * Interaction input that was automatically detected when the interaction started to be tracked, * if any. */ - val interactionInput: DeliveredInput? + val interactionInput: InteractionStartInput? /** * The number of frames that were rendered between the first and the last event in [sentEvents] @@ -372,7 +377,7 @@ class SentEvent( ) class InteractionResultDataPayload( - override val interactionInput: DeliveredInput?, + override val interactionInput: InteractionStartInput?, override val runningFrameCount: Int, override val sentEvents: List>, ) : InteractionResultData @@ -414,6 +419,7 @@ sealed class InteractionResult( is Canceled<*> -> "cancelReason=\"$cancelReason\", startToCancel=${ startToCancel.toString(MILLISECONDS) }, " + is Finished<*> -> "startToEndFrameRendered=${ startToEndFrameRendered.toString(MILLISECONDS) }, " @@ -424,7 +430,7 @@ sealed class InteractionResult( interactionInput?.let { append( "inputToStart=${ - (sentEvents.first().uptime - it.eventUptime).toString( + (sentEvents.first().uptime - it.inputUptime).toString( MILLISECONDS ) }, " diff --git a/papa/src/main/java/papa/InteractionStartInput.kt b/papa/src/main/java/papa/InteractionStartInput.kt new file mode 100644 index 0000000..b2aca3a --- /dev/null +++ b/papa/src/main/java/papa/InteractionStartInput.kt @@ -0,0 +1,7 @@ +package papa + +import kotlin.time.Duration + +interface InteractionStartInput { + val inputUptime: Duration +}