Loading packages/SystemUI/src/com/android/systemui/biometrics/udfps/EllipseOverlapDetector.kt +2 −28 Original line number Diff line number Diff line Loading @@ -22,9 +22,7 @@ import android.util.Log import com.android.systemui.biometrics.EllipseOverlapDetectorParams import com.android.systemui.dagger.SysUISingleton import kotlin.math.cos import kotlin.math.pow import kotlin.math.sin import kotlin.math.sqrt private enum class SensorPixelPosition { OUTSIDE, // Pixel that falls outside of sensor circle Loading @@ -42,8 +40,8 @@ private val TAG = "EllipseOverlapDetector" @SysUISingleton class EllipseOverlapDetector(private val params: EllipseOverlapDetectorParams) : OverlapDetector { override fun isGoodOverlap(touchData: NormalizedTouchData, nativeSensorBounds: Rect): Boolean { // First, check if entire ellipse is within the sensor if (isEllipseWithinSensor(touchData, nativeSensorBounds)) { // First, check if touch is within bounding box, if (nativeSensorBounds.contains(touchData.x.toInt(), touchData.y.toInt())) { return true } Loading Loading @@ -119,28 +117,4 @@ class EllipseOverlapDetector(private val params: EllipseOverlapDetectorParams) : return result <= 1 } /** Returns whether the entire ellipse is contained within the sensor area */ private fun isEllipseWithinSensor( touchData: NormalizedTouchData, nativeSensorBounds: Rect ): Boolean { val a2 = (touchData.minor / 2.0).pow(2.0) val b2 = (touchData.major / 2.0).pow(2.0) val sin2a = sin(touchData.orientation.toDouble()).pow(2.0) val cos2a = cos(touchData.orientation.toDouble()).pow(2.0) val cx = sqrt(a2 * cos2a + b2 * sin2a) val cy = sqrt(a2 * sin2a + b2 * cos2a) val ellipseRect = Rect( (-cx + touchData.x).toInt(), (-cy + touchData.y).toInt(), (cx + touchData.x).toInt(), (cy + touchData.y).toInt() ) return nativeSensorBounds.contains(ellipseRect) } } packages/SystemUI/tests/src/com/android/systemui/biometrics/udfps/EllipseOverlapDetectorTest.kt +15 −5 Original line number Diff line number Diff line Loading @@ -61,7 +61,7 @@ class EllipseOverlapDetectorTest(val testCase: TestCase) : SysuiTestCase() { @JvmStatic fun data(): List<TestCase> = listOf( genTestCases( genPositiveTestCases( innerXs = listOf(SENSOR.left, SENSOR.right, SENSOR.centerX()), innerYs = listOf(SENSOR.top, SENSOR.bottom, SENSOR.centerY()), outerXs = listOf(SENSOR.left - 1, SENSOR.right + 1), Loading @@ -70,9 +70,7 @@ class EllipseOverlapDetectorTest(val testCase: TestCase) : SysuiTestCase() { major = 300f, expected = true ), genTestCases( innerXs = listOf(SENSOR.left, SENSOR.right), innerYs = listOf(SENSOR.top, SENSOR.bottom), genNegativeTestCase( outerXs = listOf(SENSOR.left - 1, SENSOR.right + 1), outerYs = listOf(SENSOR.top - 1, SENSOR.bottom + 1), minor = 100f, Loading Loading @@ -107,7 +105,7 @@ private val TOUCH_DATA = private val SENSOR = Rect(100 /* left */, 200 /* top */, 300 /* right */, 400 /* bottom */) private fun genTestCases( private fun genPositiveTestCases( innerXs: List<Int>, innerYs: List<Int>, outerXs: List<Int>, Loading @@ -122,3 +120,15 @@ private fun genTestCases( } } } private fun genNegativeTestCase( outerXs: List<Int>, outerYs: List<Int>, minor: Float, major: Float, expected: Boolean ): List<EllipseOverlapDetectorTest.TestCase> { return outerXs.flatMap { x -> outerYs.map { y -> EllipseOverlapDetectorTest.TestCase(x, y, minor, major, expected) } } } Loading
packages/SystemUI/src/com/android/systemui/biometrics/udfps/EllipseOverlapDetector.kt +2 −28 Original line number Diff line number Diff line Loading @@ -22,9 +22,7 @@ import android.util.Log import com.android.systemui.biometrics.EllipseOverlapDetectorParams import com.android.systemui.dagger.SysUISingleton import kotlin.math.cos import kotlin.math.pow import kotlin.math.sin import kotlin.math.sqrt private enum class SensorPixelPosition { OUTSIDE, // Pixel that falls outside of sensor circle Loading @@ -42,8 +40,8 @@ private val TAG = "EllipseOverlapDetector" @SysUISingleton class EllipseOverlapDetector(private val params: EllipseOverlapDetectorParams) : OverlapDetector { override fun isGoodOverlap(touchData: NormalizedTouchData, nativeSensorBounds: Rect): Boolean { // First, check if entire ellipse is within the sensor if (isEllipseWithinSensor(touchData, nativeSensorBounds)) { // First, check if touch is within bounding box, if (nativeSensorBounds.contains(touchData.x.toInt(), touchData.y.toInt())) { return true } Loading Loading @@ -119,28 +117,4 @@ class EllipseOverlapDetector(private val params: EllipseOverlapDetectorParams) : return result <= 1 } /** Returns whether the entire ellipse is contained within the sensor area */ private fun isEllipseWithinSensor( touchData: NormalizedTouchData, nativeSensorBounds: Rect ): Boolean { val a2 = (touchData.minor / 2.0).pow(2.0) val b2 = (touchData.major / 2.0).pow(2.0) val sin2a = sin(touchData.orientation.toDouble()).pow(2.0) val cos2a = cos(touchData.orientation.toDouble()).pow(2.0) val cx = sqrt(a2 * cos2a + b2 * sin2a) val cy = sqrt(a2 * sin2a + b2 * cos2a) val ellipseRect = Rect( (-cx + touchData.x).toInt(), (-cy + touchData.y).toInt(), (cx + touchData.x).toInt(), (cy + touchData.y).toInt() ) return nativeSensorBounds.contains(ellipseRect) } }
packages/SystemUI/tests/src/com/android/systemui/biometrics/udfps/EllipseOverlapDetectorTest.kt +15 −5 Original line number Diff line number Diff line Loading @@ -61,7 +61,7 @@ class EllipseOverlapDetectorTest(val testCase: TestCase) : SysuiTestCase() { @JvmStatic fun data(): List<TestCase> = listOf( genTestCases( genPositiveTestCases( innerXs = listOf(SENSOR.left, SENSOR.right, SENSOR.centerX()), innerYs = listOf(SENSOR.top, SENSOR.bottom, SENSOR.centerY()), outerXs = listOf(SENSOR.left - 1, SENSOR.right + 1), Loading @@ -70,9 +70,7 @@ class EllipseOverlapDetectorTest(val testCase: TestCase) : SysuiTestCase() { major = 300f, expected = true ), genTestCases( innerXs = listOf(SENSOR.left, SENSOR.right), innerYs = listOf(SENSOR.top, SENSOR.bottom), genNegativeTestCase( outerXs = listOf(SENSOR.left - 1, SENSOR.right + 1), outerYs = listOf(SENSOR.top - 1, SENSOR.bottom + 1), minor = 100f, Loading Loading @@ -107,7 +105,7 @@ private val TOUCH_DATA = private val SENSOR = Rect(100 /* left */, 200 /* top */, 300 /* right */, 400 /* bottom */) private fun genTestCases( private fun genPositiveTestCases( innerXs: List<Int>, innerYs: List<Int>, outerXs: List<Int>, Loading @@ -122,3 +120,15 @@ private fun genTestCases( } } } private fun genNegativeTestCase( outerXs: List<Int>, outerYs: List<Int>, minor: Float, major: Float, expected: Boolean ): List<EllipseOverlapDetectorTest.TestCase> { return outerXs.flatMap { x -> outerYs.map { y -> EllipseOverlapDetectorTest.TestCase(x, y, minor, major, expected) } } }