react-native-rectangle-doc-scanner 4.12.0 → 4.14.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -541,25 +541,25 @@ class CameraController(
541
541
  val centerX = viewWidth / 2f
542
542
  val centerY = viewHeight / 2f
543
543
 
544
+ // Rotate to match display orientation.
544
545
  val matrix = Matrix()
545
-
546
- // Apply transformations in correct order:
547
- // 1. Translate to center
548
- matrix.postTranslate(-centerX, -centerY)
549
-
550
- // 2. Rotate around origin
551
546
  if (rotation != 0) {
552
- matrix.postRotate(rotation.toFloat())
547
+ matrix.postRotate(rotation.toFloat(), centerX, centerY)
553
548
  }
554
-
555
- // 3. Scale to fill view
556
- val scale = max(viewWidth / bufferWidth, viewHeight / bufferHeight)
557
- matrix.postScale(scale, scale)
558
-
559
- // 4. Translate back to center
560
- matrix.postTranslate(centerX, centerY)
561
-
562
549
  previewView.setTransform(matrix)
550
+
551
+ // Center-crop to fill the view.
552
+ val viewAspect = viewWidth / viewHeight
553
+ val bufferAspect = bufferWidth / bufferHeight
554
+ previewView.pivotX = centerX
555
+ previewView.pivotY = centerY
556
+ if (bufferAspect > viewAspect) {
557
+ previewView.scaleX = bufferAspect / viewAspect
558
+ previewView.scaleY = 1f
559
+ } else {
560
+ previewView.scaleX = 1f
561
+ previewView.scaleY = viewAspect / bufferAspect
562
+ }
563
563
  }
564
564
 
565
565
  private fun chooseBestSize(
@@ -602,11 +602,12 @@ class CameraController(
602
602
  }
603
603
 
604
604
  val bestDiff = pool.minOf { aspectDiff(it) }
605
- // Use tight tolerance (0.05) to get the best aspect ratio match
606
- val close = pool.filter { aspectDiff(it) <= bestDiff + 0.05 }
605
+ // Use very tight tolerance (0.001) to get only the best aspect ratio matches
606
+ val close = pool.filter { aspectDiff(it) <= bestDiff + 0.001 }
607
607
 
608
+ // Among best aspect ratio matches, prefer higher resolution
608
609
  val selected = close.maxByOrNull { it.width * it.height } ?: pool.maxByOrNull { it.width * it.height }
609
- Log.d(TAG, "[SIZE_SELECTION] Best aspect diff: $bestDiff, selected: ${selected?.width}x${selected?.height}")
610
+ Log.d(TAG, "[SIZE_SELECTION] Best aspect diff: $bestDiff, candidates: ${close.size}, selected: ${selected?.width}x${selected?.height}")
610
611
  return selected
611
612
  }
612
613
 
@@ -308,18 +308,14 @@ class DocumentDetector {
308
308
  * Order points in consistent order: topLeft, topRight, bottomLeft, bottomRight
309
309
  */
310
310
  private fun orderPoints(points: Array<Point>): Rectangle {
311
- // Sort by y-coordinate
312
- val sorted = points.sortedBy { it.y }
313
-
314
- // Top two points
315
- val topPoints = sorted.take(2).sortedBy { it.x }
316
- val topLeft = topPoints[0]
317
- val topRight = topPoints[1]
318
-
319
- // Bottom two points
320
- val bottomPoints = sorted.takeLast(2).sortedBy { it.x }
321
- val bottomLeft = bottomPoints[0]
322
- val bottomRight = bottomPoints[1]
311
+ // Use sum/diff ordering for robustness under rotation.
312
+ val sortedBySum = points.sortedBy { it.x + it.y }
313
+ val sortedByDiff = points.sortedBy { it.x - it.y }
314
+
315
+ val topLeft = sortedBySum.first()
316
+ val bottomRight = sortedBySum.last()
317
+ val topRight = sortedByDiff.first()
318
+ val bottomLeft = sortedByDiff.last()
323
319
 
324
320
  return Rectangle(topLeft, topRight, bottomLeft, bottomRight)
325
321
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "react-native-rectangle-doc-scanner",
3
- "version": "4.12.0",
3
+ "version": "4.14.0",
4
4
  "description": "Native-backed document scanner for React Native with customizable overlays.",
5
5
  "license": "MIT",
6
6
  "main": "dist/index.js",