Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[RUM-7018] RN Image Recording Support #2435

6 changes: 6 additions & 0 deletions dd-sdk-android-internal/api/apiSurface
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,12 @@ sealed class com.datadog.android.internal.telemetry.InternalTelemetryEvent
constructor(Boolean, Boolean, Boolean, MutableMap<String, Any?> = mutableMapOf())
object InterceptorInstantiated : InternalTelemetryEvent
fun ByteArray.toHexString(): String
object com.datadog.android.internal.utils.ImageViewUtils
fun resolveParentRectAbsPosition(android.view.View): android.graphics.Rect
fun calculateClipping(android.graphics.Rect, android.graphics.Rect, Float): android.graphics.Rect
fun resolveContentRectWithScaling(android.widget.ImageView, android.graphics.drawable.Drawable): android.graphics.Rect
fun Int.densityNormalized(Float): Int
fun Long.densityNormalized(Float): Long
fun Throwable.loggableStackTrace(): String
annotation com.datadog.tools.annotation.NoOpImplementation
constructor(Boolean = false)
15 changes: 15 additions & 0 deletions dd-sdk-android-internal/api/dd-sdk-android-internal.api
Original file line number Diff line number Diff line change
Expand Up @@ -108,6 +108,21 @@ public final class com/datadog/android/internal/utils/ByteArrayExtKt {
public static final fun toHexString ([B)Ljava/lang/String;
}

public final class com/datadog/android/internal/utils/ImageViewUtils {
public static final field INSTANCE Lcom/datadog/android/internal/utils/ImageViewUtils;
public final fun calculateClipping (Landroid/graphics/Rect;Landroid/graphics/Rect;F)Landroid/graphics/Rect;
public final fun resolveContentRectWithScaling (Landroid/widget/ImageView;Landroid/graphics/drawable/Drawable;)Landroid/graphics/Rect;
public final fun resolveParentRectAbsPosition (Landroid/view/View;)Landroid/graphics/Rect;
}

public final class com/datadog/android/internal/utils/IntExtKt {
public static final fun densityNormalized (IF)I
}

public final class com/datadog/android/internal/utils/LongExtKt {
public static final fun densityNormalized (JF)J
}

public final class com/datadog/android/internal/utils/ThrowableExtKt {
public static final fun loggableStackTrace (Ljava/lang/Throwable;)Ljava/lang/String;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,17 +4,25 @@
* Copyright 2016-Present Datadog, Inc.
*/

package com.datadog.android.sessionreplay.internal.utils
package com.datadog.android.internal.utils

import android.graphics.Rect
import android.graphics.drawable.Drawable
import android.view.View
import android.widget.ImageView
import com.datadog.android.sessionreplay.internal.recorder.densityNormalized
import com.datadog.android.sessionreplay.model.MobileSegment

internal object ImageViewUtils {
internal fun resolveParentRectAbsPosition(view: View): Rect {
/**
* A collection of view utility functions for resolving absolute
* positions, clipping bounds, and other useful data for
* image views operations.
*/
object ImageViewUtils {
/**
* Resolves the absolute position on the screen of the given [View].
* @param view: the [View].
* @return the [Rect] representing the absolute position of the view.
*/
fun resolveParentRectAbsPosition(view: View): Rect {
val coords = IntArray(2)
// this will always have size >= 2
@Suppress("UnsafeThirdPartyFunctionCall")
Expand All @@ -31,7 +39,15 @@ internal object ImageViewUtils {
)
}

internal fun calculateClipping(parentRect: Rect, childRect: Rect, density: Float): MobileSegment.WireframeClip {
/**
* Calculates the clipping [Rect] of the given child [Rect] using its parent [Rect] and
* the screen density.
* @param parentRect: the parent [Rect].
* @param childRect: the child [Rect].
* @param density: the screen density.
* @return the clipping [Rect].
*/
fun calculateClipping(parentRect: Rect, childRect: Rect, density: Float): Rect {
val left = if (childRect.left < parentRect.left) {
parentRect.left - childRect.left
} else {
Expand All @@ -52,16 +68,21 @@ internal object ImageViewUtils {
} else {
0
}

return MobileSegment.WireframeClip(
left = left.densityNormalized(density).toLong(),
top = top.densityNormalized(density).toLong(),
right = right.densityNormalized(density).toLong(),
bottom = bottom.densityNormalized(density).toLong()
return Rect(
left.densityNormalized(density),
top.densityNormalized(density),
right.densityNormalized(density),
bottom.densityNormalized(density)
)
}

internal fun resolveContentRectWithScaling(
/**
* Resolves the [Drawable] content [Rect] using the given [ImageView] scale type.
* @param imageView: the [ImageView].
* @param drawable: the [Drawable].
* @return the resolved content [Rect].
*/
fun resolveContentRectWithScaling(
imageView: ImageView,
drawable: Drawable
): Rect {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
* Copyright 2016-Present Datadog, Inc.
*/

package com.datadog.android.sessionreplay.internal.recorder
package com.datadog.android.internal.utils

/**
* Normalizes an Int value (font size, view dimension, view position, etc.) according with the
Expand All @@ -13,7 +13,7 @@ package com.datadog.android.sessionreplay.internal.recorder
* view.height/2.
* @param density
*/
internal fun Int.densityNormalized(density: Float): Int {
fun Int.densityNormalized(density: Float): Int {
if (density == 0f) {
return this
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
* Copyright 2016-Present Datadog, Inc.
*/

package com.datadog.android.sessionreplay.internal.recorder
package com.datadog.android.internal.utils

/**
* Normalizes a Long value (font size, view dimension, view position, etc.) according with the
Expand All @@ -13,7 +13,7 @@ package com.datadog.android.sessionreplay.internal.recorder
* view.height/2.
* @param density
*/
internal fun Long.densityNormalized(density: Float): Long {
fun Long.densityNormalized(density: Float): Long {
if (density == 0f) {
return this
}
Expand Down
16 changes: 10 additions & 6 deletions features/dd-sdk-android-session-replay/api/apiSurface
Original file line number Diff line number Diff line change
Expand Up @@ -59,18 +59,18 @@ interface com.datadog.android.sessionreplay.internal.recorder.obfuscator.StringO
fun obfuscate(String): String
companion object
fun getStringObfuscator(): StringObfuscator
class com.datadog.android.sessionreplay.internal.recorder.resources.DefaultDrawableCopier : DrawableCopier
override fun copy(android.graphics.drawable.Drawable, android.content.res.Resources): android.graphics.drawable.Drawable?
interface com.datadog.android.sessionreplay.internal.recorder.resources.DrawableCopier
fun copy(android.graphics.drawable.Drawable, android.content.res.Resources): android.graphics.drawable.Drawable?
data class com.datadog.android.sessionreplay.recorder.MappingContext
constructor(SystemInformation, com.datadog.android.sessionreplay.utils.ImageWireframeHelper, com.datadog.android.sessionreplay.TextAndInputPrivacy, com.datadog.android.sessionreplay.ImagePrivacy, Boolean = false)
interface com.datadog.android.sessionreplay.recorder.OptionSelectorDetector
fun isOptionSelector(android.view.ViewGroup): Boolean
data class com.datadog.android.sessionreplay.recorder.SystemInformation
constructor(com.datadog.android.sessionreplay.utils.GlobalBounds, Int = Configuration.ORIENTATION_UNDEFINED, Float, String? = null)
abstract class com.datadog.android.sessionreplay.recorder.mapper.BaseAsyncBackgroundWireframeMapper<T: android.view.View> : BaseWireframeMapper<T>
constructor(com.datadog.android.sessionreplay.utils.ViewIdentifierResolver, com.datadog.android.sessionreplay.utils.ColorStringFormatter, com.datadog.android.sessionreplay.utils.ViewBoundsResolver, com.datadog.android.sessionreplay.utils.DrawableToColorMapper)
override fun map(T, com.datadog.android.sessionreplay.recorder.MappingContext, com.datadog.android.sessionreplay.utils.AsyncJobStatusCallback, com.datadog.android.api.InternalLogger): List<com.datadog.android.sessionreplay.model.MobileSegment.Wireframe>
protected open fun resolveViewBackground(android.view.View, com.datadog.android.sessionreplay.recorder.MappingContext, com.datadog.android.sessionreplay.utils.AsyncJobStatusCallback, com.datadog.android.api.InternalLogger): com.datadog.android.sessionreplay.model.MobileSegment.Wireframe?
protected open fun resolveBackgroundAsShapeWireframe(android.view.View, com.datadog.android.sessionreplay.utils.GlobalBounds, Int, Int, com.datadog.android.sessionreplay.model.MobileSegment.ShapeStyle?): com.datadog.android.sessionreplay.model.MobileSegment.Wireframe.ShapeWireframe?
protected open fun resolveBackgroundAsImageWireframe(android.view.View, com.datadog.android.sessionreplay.utils.GlobalBounds, Int, Int, com.datadog.android.sessionreplay.recorder.MappingContext, com.datadog.android.sessionreplay.utils.AsyncJobStatusCallback): com.datadog.android.sessionreplay.model.MobileSegment.Wireframe?
companion object
open class com.datadog.android.sessionreplay.recorder.mapper.BaseViewGroupMapper<T: android.view.ViewGroup> : BaseAsyncBackgroundWireframeMapper<T>, TraverseAllChildrenMapper<T>
constructor(com.datadog.android.sessionreplay.utils.ViewIdentifierResolver, com.datadog.android.sessionreplay.utils.ColorStringFormatter, com.datadog.android.sessionreplay.utils.ViewBoundsResolver, com.datadog.android.sessionreplay.utils.DrawableToColorMapper)
Expand All @@ -83,7 +83,7 @@ class com.datadog.android.sessionreplay.recorder.mapper.EditTextMapper : TextVie
override fun resolveCapturedText(android.widget.EditText, com.datadog.android.sessionreplay.TextAndInputPrivacy, Boolean): String
companion object
open class com.datadog.android.sessionreplay.recorder.mapper.ImageViewMapper : BaseAsyncBackgroundWireframeMapper<android.widget.ImageView>
constructor(com.datadog.android.sessionreplay.utils.ViewIdentifierResolver, com.datadog.android.sessionreplay.utils.ColorStringFormatter, com.datadog.android.sessionreplay.utils.ViewBoundsResolver, com.datadog.android.sessionreplay.utils.DrawableToColorMapper)
constructor(com.datadog.android.sessionreplay.utils.ViewIdentifierResolver, com.datadog.android.sessionreplay.utils.ColorStringFormatter, com.datadog.android.sessionreplay.utils.ViewBoundsResolver, com.datadog.android.sessionreplay.utils.DrawableToColorMapper, com.datadog.android.sessionreplay.recorder.resources.DrawableCopier)
override fun map(android.widget.ImageView, com.datadog.android.sessionreplay.recorder.MappingContext, com.datadog.android.sessionreplay.utils.AsyncJobStatusCallback, com.datadog.android.api.InternalLogger): List<com.datadog.android.sessionreplay.model.MobileSegment.Wireframe>
open class com.datadog.android.sessionreplay.recorder.mapper.TextViewMapper<T: android.widget.TextView> : BaseAsyncBackgroundWireframeMapper<T>
constructor(com.datadog.android.sessionreplay.utils.ViewIdentifierResolver, com.datadog.android.sessionreplay.utils.ColorStringFormatter, com.datadog.android.sessionreplay.utils.ViewBoundsResolver, com.datadog.android.sessionreplay.utils.DrawableToColorMapper)
Expand All @@ -93,6 +93,10 @@ open class com.datadog.android.sessionreplay.recorder.mapper.TextViewMapper<T: a
interface com.datadog.android.sessionreplay.recorder.mapper.TraverseAllChildrenMapper<T: android.view.ViewGroup> : WireframeMapper<T>
interface com.datadog.android.sessionreplay.recorder.mapper.WireframeMapper<T: android.view.View>
fun map(T, com.datadog.android.sessionreplay.recorder.MappingContext, com.datadog.android.sessionreplay.utils.AsyncJobStatusCallback, com.datadog.android.api.InternalLogger): List<com.datadog.android.sessionreplay.model.MobileSegment.Wireframe>
class com.datadog.android.sessionreplay.recorder.resources.DefaultDrawableCopier : DrawableCopier
override fun copy(android.graphics.drawable.Drawable, android.content.res.Resources): android.graphics.drawable.Drawable?
interface com.datadog.android.sessionreplay.recorder.resources.DrawableCopier
fun copy(android.graphics.drawable.Drawable, android.content.res.Resources): android.graphics.drawable.Drawable?
open class com.datadog.android.sessionreplay.utils.AndroidMDrawableToColorMapper : LegacyDrawableToColorMapper
constructor(List<DrawableToColorMapper> = emptyList())
override fun resolveRippleDrawable(android.graphics.drawable.RippleDrawable, com.datadog.android.api.InternalLogger): Int?
Expand Down Expand Up @@ -126,7 +130,7 @@ data class com.datadog.android.sessionreplay.utils.GlobalBounds
constructor(Long, Long, Long, Long)
interface com.datadog.android.sessionreplay.utils.ImageWireframeHelper
fun createImageWireframeByBitmap(Long, GlobalBounds, android.graphics.Bitmap, Float, Boolean, com.datadog.android.sessionreplay.ImagePrivacy, AsyncJobStatusCallback, com.datadog.android.sessionreplay.model.MobileSegment.WireframeClip? = null, com.datadog.android.sessionreplay.model.MobileSegment.ShapeStyle? = null, com.datadog.android.sessionreplay.model.MobileSegment.ShapeBorder? = null): com.datadog.android.sessionreplay.model.MobileSegment.Wireframe?
fun createImageWireframeByDrawable(android.view.View, com.datadog.android.sessionreplay.ImagePrivacy, Int, Long, Long, Int, Int, Boolean, android.graphics.drawable.Drawable, com.datadog.android.sessionreplay.internal.recorder.resources.DrawableCopier = DefaultDrawableCopier(), AsyncJobStatusCallback, com.datadog.android.sessionreplay.model.MobileSegment.WireframeClip? = null, com.datadog.android.sessionreplay.model.MobileSegment.ShapeStyle? = null, com.datadog.android.sessionreplay.model.MobileSegment.ShapeBorder? = null, String? = DRAWABLE_CHILD_NAME, String?): com.datadog.android.sessionreplay.model.MobileSegment.Wireframe?
fun createImageWireframeByDrawable(android.view.View, com.datadog.android.sessionreplay.ImagePrivacy, Int, Long, Long, Int, Int, Boolean, android.graphics.drawable.Drawable, com.datadog.android.sessionreplay.recorder.resources.DrawableCopier = DefaultDrawableCopier(), AsyncJobStatusCallback, com.datadog.android.sessionreplay.model.MobileSegment.WireframeClip? = null, com.datadog.android.sessionreplay.model.MobileSegment.ShapeStyle? = null, com.datadog.android.sessionreplay.model.MobileSegment.ShapeBorder? = null, String? = DRAWABLE_CHILD_NAME, String?): com.datadog.android.sessionreplay.model.MobileSegment.Wireframe?
fun createCompoundDrawableWireframes(android.widget.TextView, com.datadog.android.sessionreplay.recorder.MappingContext, Int, String?, AsyncJobStatusCallback): MutableList<com.datadog.android.sessionreplay.model.MobileSegment.Wireframe>
companion object
open class com.datadog.android.sessionreplay.utils.LegacyDrawableToColorMapper : DrawableToColorMapper
Expand Down
Loading