@capgo/camera-preview 7.4.0-beta.7 → 7.4.0-beta.8
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.
- package/README.md +62 -28
- package/android/.gradle/8.14.2/checksums/checksums.lock +0 -0
- package/android/.gradle/8.14.2/checksums/md5-checksums.bin +0 -0
- package/android/.gradle/8.14.2/checksums/sha1-checksums.bin +0 -0
- package/android/.gradle/8.14.2/executionHistory/executionHistory.bin +0 -0
- package/android/.gradle/8.14.2/executionHistory/executionHistory.lock +0 -0
- package/android/.gradle/8.14.2/fileHashes/fileHashes.bin +0 -0
- package/android/.gradle/8.14.2/fileHashes/fileHashes.lock +0 -0
- package/android/.gradle/8.14.2/fileHashes/resourceHashesCache.bin +0 -0
- package/android/.gradle/buildOutputCleanup/buildOutputCleanup.lock +0 -0
- package/android/.gradle/buildOutputCleanup/cache.properties +1 -1
- package/android/.gradle/buildOutputCleanup/outputFiles.bin +0 -0
- package/android/.gradle/file-system.probe +0 -0
- package/android/build.gradle +1 -0
- package/android/src/main/java/com/ahm/capacitor/camera/preview/CameraPreview.java +127 -14
- package/android/src/main/java/com/ahm/capacitor/camera/preview/CameraXView.java +479 -29
- package/android/src/main/java/com/ahm/capacitor/camera/preview/GridOverlayView.java +2 -0
- package/dist/docs.json +46 -7
- package/dist/esm/definitions.d.ts +42 -5
- package/dist/esm/definitions.js.map +1 -1
- package/dist/esm/web.d.ts +25 -1
- package/dist/esm/web.js +81 -9
- package/dist/esm/web.js.map +1 -1
- package/dist/plugin.cjs.js +81 -9
- package/dist/plugin.cjs.js.map +1 -1
- package/dist/plugin.js +81 -9
- package/dist/plugin.js.map +1 -1
- package/ios/Sources/CapgoCameraPreview/CameraController.swift +95 -18
- package/ios/Sources/CapgoCameraPreview/Plugin.swift +271 -91
- package/package.json +1 -1
- package/android/.gradle/config.properties +0 -2
- package/android/.idea/AndroidProjectSystem.xml +0 -6
- package/android/.idea/caches/deviceStreaming.xml +0 -811
- package/android/.idea/compiler.xml +0 -6
- package/android/.idea/gradle.xml +0 -18
- package/android/.idea/migrations.xml +0 -10
- package/android/.idea/misc.xml +0 -10
- package/android/.idea/runConfigurations.xml +0 -17
- package/android/.idea/vcs.xml +0 -6
- package/android/.idea/workspace.xml +0 -55
- package/android/local.properties +0 -8
|
@@ -62,11 +62,14 @@ public class CameraPreview: CAPPlugin, CAPBridgedPlugin, CLLocationManagerDelega
|
|
|
62
62
|
CAPPluginMethod(name: "setAspectRatio", returnType: CAPPluginReturnPromise),
|
|
63
63
|
CAPPluginMethod(name: "getAspectRatio", returnType: CAPPluginReturnPromise),
|
|
64
64
|
CAPPluginMethod(name: "setGridMode", returnType: CAPPluginReturnPromise),
|
|
65
|
-
CAPPluginMethod(name: "getGridMode", returnType: CAPPluginReturnPromise)
|
|
65
|
+
CAPPluginMethod(name: "getGridMode", returnType: CAPPluginReturnPromise),
|
|
66
|
+
CAPPluginMethod(name: "getPreviewSize", returnType: CAPPluginReturnPromise),
|
|
67
|
+
CAPPluginMethod(name: "setPreviewSize", returnType: CAPPluginReturnPromise)
|
|
66
68
|
]
|
|
67
69
|
// Camera state tracking
|
|
68
70
|
private var isInitializing: Bool = false
|
|
69
71
|
private var isInitialized: Bool = false
|
|
72
|
+
private var backgroundSession: AVCaptureSession?
|
|
70
73
|
|
|
71
74
|
var previewView: UIView!
|
|
72
75
|
var cameraPosition = String()
|
|
@@ -138,14 +141,26 @@ public class CameraPreview: CAPPlugin, CAPBridgedPlugin, CLLocationManagerDelega
|
|
|
138
141
|
let paddingBottom = self.paddingBottom ?? 0
|
|
139
142
|
let height = heightValue - paddingBottom
|
|
140
143
|
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
144
|
+
// Handle auto-centering during rotation
|
|
145
|
+
if posX == -1 || posY == -1 {
|
|
146
|
+
// Trigger full recalculation for auto-centered views
|
|
147
|
+
self.updateCameraFrame()
|
|
148
|
+
} else {
|
|
149
|
+
// Manual positioning - use original rotation logic with no animation
|
|
150
|
+
CATransaction.begin()
|
|
151
|
+
CATransaction.setDisableActions(true)
|
|
152
|
+
|
|
153
|
+
if UIWindow.isLandscape {
|
|
154
|
+
previewView.frame = CGRect(x: posY, y: posX, width: max(height, width), height: min(height, width))
|
|
155
|
+
self.cameraController.previewLayer?.frame = previewView.bounds
|
|
156
|
+
}
|
|
145
157
|
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
158
|
+
if UIWindow.isPortrait {
|
|
159
|
+
previewView.frame = CGRect(x: posX, y: posY, width: min(height, width), height: max(height, width))
|
|
160
|
+
self.cameraController.previewLayer?.frame = previewView.bounds
|
|
161
|
+
}
|
|
162
|
+
|
|
163
|
+
CATransaction.commit()
|
|
149
164
|
}
|
|
150
165
|
|
|
151
166
|
if let connection = self.cameraController.fileVideoOutput?.connection(with: .video) {
|
|
@@ -165,11 +180,14 @@ public class CameraPreview: CAPPlugin, CAPBridgedPlugin, CLLocationManagerDelega
|
|
|
165
180
|
|
|
166
181
|
cameraController.updateVideoOrientation()
|
|
167
182
|
|
|
168
|
-
|
|
183
|
+
cameraController.updateVideoOrientation()
|
|
169
184
|
|
|
170
|
-
// Update grid overlay frame if it exists
|
|
185
|
+
// Update grid overlay frame if it exists - no animation
|
|
171
186
|
if let gridOverlay = self.cameraController.gridOverlayView {
|
|
187
|
+
CATransaction.begin()
|
|
188
|
+
CATransaction.setDisableActions(true)
|
|
172
189
|
gridOverlay.frame = previewView.bounds
|
|
190
|
+
CATransaction.commit()
|
|
173
191
|
}
|
|
174
192
|
|
|
175
193
|
// Ensure webview remains transparent after rotation
|
|
@@ -183,9 +201,65 @@ public class CameraPreview: CAPPlugin, CAPBridgedPlugin, CLLocationManagerDelega
|
|
|
183
201
|
call.reject("camera not started")
|
|
184
202
|
return
|
|
185
203
|
}
|
|
186
|
-
|
|
204
|
+
|
|
205
|
+
guard let newAspectRatio = call.getString("aspectRatio") else {
|
|
206
|
+
call.reject("aspectRatio parameter is required")
|
|
207
|
+
return
|
|
208
|
+
}
|
|
209
|
+
|
|
210
|
+
self.aspectRatio = newAspectRatio
|
|
211
|
+
|
|
212
|
+
// When aspect ratio changes, calculate maximum size possible from current position
|
|
213
|
+
if let posX = self.posX, let posY = self.posY {
|
|
214
|
+
let webViewWidth = self.webView?.frame.width ?? UIScreen.main.bounds.width
|
|
215
|
+
let webViewHeight = self.webView?.frame.height ?? UIScreen.main.bounds.height
|
|
216
|
+
let paddingBottom = self.paddingBottom ?? 0
|
|
217
|
+
|
|
218
|
+
// Calculate available space from current position
|
|
219
|
+
let availableWidth: CGFloat
|
|
220
|
+
let availableHeight: CGFloat
|
|
221
|
+
|
|
222
|
+
if posX == -1 || posY == -1 {
|
|
223
|
+
// Auto-centering mode - use full dimensions
|
|
224
|
+
availableWidth = webViewWidth
|
|
225
|
+
availableHeight = webViewHeight - paddingBottom
|
|
226
|
+
} else {
|
|
227
|
+
// Manual positioning - calculate remaining space
|
|
228
|
+
availableWidth = webViewWidth - posX
|
|
229
|
+
availableHeight = webViewHeight - posY - paddingBottom
|
|
230
|
+
}
|
|
231
|
+
|
|
232
|
+
// Parse aspect ratio - convert to portrait orientation for camera use
|
|
233
|
+
let ratioParts = newAspectRatio.split(separator: ":").map { Double($0) ?? 1.0 }
|
|
234
|
+
// For camera, we want portrait orientation: 4:3 becomes 3:4, 16:9 becomes 9:16
|
|
235
|
+
let ratio = ratioParts[1] / ratioParts[0]
|
|
236
|
+
|
|
237
|
+
// Calculate maximum size that fits the aspect ratio in available space
|
|
238
|
+
let maxWidthByHeight = availableHeight * CGFloat(ratio)
|
|
239
|
+
let maxHeightByWidth = availableWidth / CGFloat(ratio)
|
|
240
|
+
|
|
241
|
+
if maxWidthByHeight <= availableWidth {
|
|
242
|
+
// Height is the limiting factor
|
|
243
|
+
self.width = maxWidthByHeight
|
|
244
|
+
self.height = availableHeight
|
|
245
|
+
} else {
|
|
246
|
+
// Width is the limiting factor
|
|
247
|
+
self.width = availableWidth
|
|
248
|
+
self.height = maxHeightByWidth
|
|
249
|
+
}
|
|
250
|
+
|
|
251
|
+
print("[CameraPreview] Aspect ratio changed to \(newAspectRatio), new size: \(self.width!)x\(self.height!)")
|
|
252
|
+
}
|
|
253
|
+
|
|
187
254
|
self.updateCameraFrame()
|
|
188
|
-
|
|
255
|
+
|
|
256
|
+
// Return the actual preview bounds
|
|
257
|
+
var result = JSObject()
|
|
258
|
+
result["x"] = Double(self.previewView.frame.origin.x)
|
|
259
|
+
result["y"] = Double(self.previewView.frame.origin.y)
|
|
260
|
+
result["width"] = Double(self.previewView.frame.width)
|
|
261
|
+
result["height"] = Double(self.previewView.frame.height)
|
|
262
|
+
call.resolve(result)
|
|
189
263
|
}
|
|
190
264
|
|
|
191
265
|
@objc func getAspectRatio(_ call: CAPPluginCall) {
|
|
@@ -358,18 +432,18 @@ public class CameraPreview: CAPPlugin, CAPBridgedPlugin, CLLocationManagerDelega
|
|
|
358
432
|
self.height = UIScreen.main.bounds.size.height
|
|
359
433
|
}
|
|
360
434
|
|
|
361
|
-
// Set x position - use
|
|
362
|
-
if let x = call.getInt("x")
|
|
363
|
-
self.posX = CGFloat(x)
|
|
435
|
+
// Set x position - use exact CSS pixel value from web view, or mark for centering
|
|
436
|
+
if let x = call.getInt("x") {
|
|
437
|
+
self.posX = CGFloat(x)
|
|
364
438
|
} else {
|
|
365
|
-
self.posX =
|
|
439
|
+
self.posX = -1 // Use -1 to indicate auto-centering
|
|
366
440
|
}
|
|
367
441
|
|
|
368
|
-
// Set y position - use
|
|
369
|
-
if let y = call.getInt("y")
|
|
370
|
-
self.posY = CGFloat(y)
|
|
442
|
+
// Set y position - use exact CSS pixel value from web view, or mark for centering
|
|
443
|
+
if let y = call.getInt("y") {
|
|
444
|
+
self.posY = CGFloat(y)
|
|
371
445
|
} else {
|
|
372
|
-
self.posY =
|
|
446
|
+
self.posY = -1 // Use -1 to indicate auto-centering
|
|
373
447
|
}
|
|
374
448
|
if call.getInt("paddingBottom") != nil {
|
|
375
449
|
self.paddingBottom = CGFloat(call.getInt("paddingBottom")!)
|
|
@@ -382,6 +456,10 @@ public class CameraPreview: CAPPlugin, CAPBridgedPlugin, CLLocationManagerDelega
|
|
|
382
456
|
self.disableAudio = call.getBool("disableAudio") ?? true
|
|
383
457
|
self.aspectRatio = call.getString("aspectRatio")
|
|
384
458
|
self.gridMode = call.getString("gridMode") ?? "none"
|
|
459
|
+
if self.aspectRatio != nil && (call.getInt("width") != nil || call.getInt("height") != nil) {
|
|
460
|
+
call.reject("Cannot set both aspectRatio and size (width/height). Use setPreviewSize after start.")
|
|
461
|
+
return
|
|
462
|
+
}
|
|
385
463
|
|
|
386
464
|
print("[CameraPreview] Camera start parameters - aspectRatio: \(String(describing: self.aspectRatio)), gridMode: \(self.gridMode)")
|
|
387
465
|
print("[CameraPreview] Screen dimensions: \(UIScreen.main.bounds.size)")
|
|
@@ -403,54 +481,73 @@ public class CameraPreview: CAPPlugin, CAPBridgedPlugin, CLLocationManagerDelega
|
|
|
403
481
|
call.reject(error.localizedDescription)
|
|
404
482
|
return
|
|
405
483
|
}
|
|
484
|
+
self.completeStartCamera(call: call)
|
|
485
|
+
}
|
|
486
|
+
}
|
|
487
|
+
}
|
|
488
|
+
})
|
|
489
|
+
}
|
|
406
490
|
|
|
407
|
-
|
|
408
|
-
|
|
409
|
-
|
|
410
|
-
|
|
411
|
-
|
|
491
|
+
override public func load() {
|
|
492
|
+
super.load()
|
|
493
|
+
// Initialize camera session in background for faster startup
|
|
494
|
+
prepareBackgroundCamera()
|
|
495
|
+
}
|
|
412
496
|
|
|
413
|
-
|
|
414
|
-
|
|
415
|
-
|
|
416
|
-
|
|
417
|
-
|
|
497
|
+
private func prepareBackgroundCamera() {
|
|
498
|
+
DispatchQueue.global(qos: .background).async {
|
|
499
|
+
AVCaptureDevice.requestAccess(for: .video) { granted in
|
|
500
|
+
guard granted else { return }
|
|
501
|
+
|
|
502
|
+
// Pre-initialize camera controller for faster startup
|
|
503
|
+
DispatchQueue.main.async {
|
|
504
|
+
self.cameraController.prepareBasicSession()
|
|
505
|
+
}
|
|
506
|
+
}
|
|
507
|
+
}
|
|
508
|
+
}
|
|
418
509
|
|
|
419
|
-
|
|
420
|
-
|
|
510
|
+
private func completeStartCamera(call: CAPPluginCall) {
|
|
511
|
+
// Create and configure the preview view first
|
|
512
|
+
self.updateCameraFrame()
|
|
421
513
|
|
|
422
|
-
|
|
423
|
-
|
|
514
|
+
// Make webview transparent - comprehensive approach
|
|
515
|
+
self.makeWebViewTransparent()
|
|
424
516
|
|
|
425
|
-
|
|
426
|
-
|
|
427
|
-
|
|
428
|
-
|
|
517
|
+
// Add the preview view to the webview itself to use same coordinate system
|
|
518
|
+
self.webView?.addSubview(self.previewView)
|
|
519
|
+
if self.toBack! {
|
|
520
|
+
self.webView?.sendSubviewToBack(self.previewView)
|
|
521
|
+
}
|
|
429
522
|
|
|
430
|
-
|
|
431
|
-
|
|
432
|
-
}
|
|
523
|
+
// Display the camera preview on the configured view
|
|
524
|
+
try? self.cameraController.displayPreview(on: self.previewView)
|
|
433
525
|
|
|
526
|
+
let frontView = self.toBack! ? self.webView : self.previewView
|
|
527
|
+
self.cameraController.setupGestures(target: frontView ?? self.previewView, enableZoom: self.enableZoom!)
|
|
434
528
|
|
|
435
|
-
|
|
436
|
-
|
|
437
|
-
|
|
529
|
+
// Add grid overlay if enabled
|
|
530
|
+
if self.gridMode != "none" {
|
|
531
|
+
self.cameraController.addGridOverlay(to: self.previewView, gridMode: self.gridMode)
|
|
532
|
+
}
|
|
438
533
|
|
|
439
|
-
|
|
440
|
-
|
|
534
|
+
if self.rotateWhenOrientationChanged == true {
|
|
535
|
+
NotificationCenter.default.addObserver(self, selector: #selector(CameraPreview.rotated), name: UIDevice.orientationDidChangeNotification, object: nil)
|
|
536
|
+
}
|
|
441
537
|
|
|
442
|
-
|
|
443
|
-
|
|
444
|
-
|
|
445
|
-
returnedObject["x"] = self.previewView.frame.origin.x as any JSValue
|
|
446
|
-
returnedObject["y"] = self.previewView.frame.origin.y as any JSValue
|
|
447
|
-
call.resolve(returnedObject)
|
|
538
|
+
// Add observers for app state changes to maintain transparency
|
|
539
|
+
NotificationCenter.default.addObserver(self, selector: #selector(CameraPreview.appDidBecomeActive), name: UIApplication.didBecomeActiveNotification, object: nil)
|
|
540
|
+
NotificationCenter.default.addObserver(self, selector: #selector(CameraPreview.appWillEnterForeground), name: UIApplication.willEnterForegroundNotification, object: nil)
|
|
448
541
|
|
|
449
|
-
|
|
450
|
-
|
|
451
|
-
}
|
|
452
|
-
})
|
|
542
|
+
self.isInitializing = false
|
|
543
|
+
self.isInitialized = true
|
|
453
544
|
|
|
545
|
+
var returnedObject = JSObject()
|
|
546
|
+
returnedObject["width"] = self.previewView.frame.width as any JSValue
|
|
547
|
+
returnedObject["height"] = self.previewView.frame.height as any JSValue
|
|
548
|
+
returnedObject["x"] = self.previewView.frame.origin.x as any JSValue
|
|
549
|
+
returnedObject["y"] = self.previewView.frame.origin.y as any JSValue
|
|
550
|
+
call.resolve(returnedObject)
|
|
454
551
|
}
|
|
455
552
|
|
|
456
553
|
@objc func flip(_ call: CAPPluginCall) {
|
|
@@ -478,8 +575,13 @@ public class CameraPreview: CAPPlugin, CAPBridgedPlugin, CLLocationManagerDelega
|
|
|
478
575
|
try self.cameraController.switchCameras()
|
|
479
576
|
|
|
480
577
|
DispatchQueue.main.async {
|
|
578
|
+
// Update preview layer frame without animation
|
|
579
|
+
CATransaction.begin()
|
|
580
|
+
CATransaction.setDisableActions(true)
|
|
481
581
|
self.cameraController.previewLayer?.frame = self.previewView.bounds
|
|
482
582
|
self.cameraController.previewLayer?.videoGravity = .resizeAspectFill
|
|
583
|
+
CATransaction.commit()
|
|
584
|
+
|
|
483
585
|
self.previewView.isUserInteractionEnabled = true
|
|
484
586
|
|
|
485
587
|
|
|
@@ -930,8 +1032,13 @@ public class CameraPreview: CAPPlugin, CAPBridgedPlugin, CLLocationManagerDelega
|
|
|
930
1032
|
try self.cameraController.swapToDevice(deviceId: deviceId)
|
|
931
1033
|
|
|
932
1034
|
DispatchQueue.main.async {
|
|
1035
|
+
// Update preview layer frame without animation
|
|
1036
|
+
CATransaction.begin()
|
|
1037
|
+
CATransaction.setDisableActions(true)
|
|
933
1038
|
self.cameraController.previewLayer?.frame = self.previewView.bounds
|
|
934
1039
|
self.cameraController.previewLayer?.videoGravity = .resizeAspectFill
|
|
1040
|
+
CATransaction.commit()
|
|
1041
|
+
|
|
935
1042
|
self.previewView.isUserInteractionEnabled = true
|
|
936
1043
|
|
|
937
1044
|
|
|
@@ -975,57 +1082,130 @@ public class CameraPreview: CAPPlugin, CAPBridgedPlugin, CLLocationManagerDelega
|
|
|
975
1082
|
}
|
|
976
1083
|
|
|
977
1084
|
private func updateCameraFrame() {
|
|
978
|
-
print("[CameraPreview] updateCameraFrame called")
|
|
979
|
-
print("[CameraPreview] width: \(String(describing: self.width)), height: \(String(describing: self.height)), posX: \(String(describing: self.posX)), posY: \(String(describing: self.posY))")
|
|
980
|
-
|
|
981
1085
|
guard let width = self.width, var height = self.height, let posX = self.posX, let posY = self.posY else {
|
|
982
|
-
print("[CameraPreview] Missing required frame parameters")
|
|
983
1086
|
return
|
|
984
1087
|
}
|
|
985
1088
|
|
|
986
1089
|
let paddingBottom = self.paddingBottom ?? 0
|
|
987
1090
|
height -= paddingBottom
|
|
988
1091
|
|
|
989
|
-
|
|
990
|
-
|
|
991
|
-
|
|
992
|
-
|
|
993
|
-
|
|
994
|
-
|
|
995
|
-
|
|
996
|
-
|
|
997
|
-
|
|
998
|
-
|
|
999
|
-
|
|
1000
|
-
|
|
1001
|
-
|
|
1002
|
-
|
|
1003
|
-
|
|
1004
|
-
|
|
1005
|
-
|
|
1006
|
-
|
|
1007
|
-
|
|
1008
|
-
|
|
1009
|
-
|
|
1010
|
-
|
|
1011
|
-
|
|
1092
|
+
// Cache webView dimensions for performance
|
|
1093
|
+
let webViewWidth = self.webView?.frame.width ?? UIScreen.main.bounds.width
|
|
1094
|
+
let webViewHeight = self.webView?.frame.height ?? UIScreen.main.bounds.height
|
|
1095
|
+
|
|
1096
|
+
var finalX = posX
|
|
1097
|
+
var finalY = posY
|
|
1098
|
+
var finalWidth = width
|
|
1099
|
+
var finalHeight = height
|
|
1100
|
+
|
|
1101
|
+
// Handle auto-centering when position is -1
|
|
1102
|
+
if posX == -1 || posY == -1 {
|
|
1103
|
+
finalWidth = webViewWidth
|
|
1104
|
+
|
|
1105
|
+
// Calculate height based on aspect ratio or use provided height
|
|
1106
|
+
if let aspectRatio = self.aspectRatio {
|
|
1107
|
+
let ratioParts = aspectRatio.split(separator: ":").compactMap { Double($0) }
|
|
1108
|
+
if ratioParts.count == 2 {
|
|
1109
|
+
// For camera, use portrait orientation: 4:3 becomes 3:4, 16:9 becomes 9:16
|
|
1110
|
+
let ratio = ratioParts[1] / ratioParts[0]
|
|
1111
|
+
finalHeight = finalWidth / CGFloat(ratio)
|
|
1112
|
+
}
|
|
1113
|
+
}
|
|
1114
|
+
|
|
1115
|
+
finalX = posX == -1 ? 0 : posX
|
|
1116
|
+
|
|
1117
|
+
if posY == -1 {
|
|
1118
|
+
let availableHeight = webViewHeight - paddingBottom
|
|
1119
|
+
finalY = finalHeight < availableHeight ? (availableHeight - finalHeight) / 2 : 0
|
|
1012
1120
|
}
|
|
1013
1121
|
}
|
|
1014
|
-
*/
|
|
1015
1122
|
|
|
1016
|
-
|
|
1123
|
+
var frame = CGRect(x: finalX, y: finalY, width: finalWidth, height: finalHeight)
|
|
1124
|
+
|
|
1125
|
+
// Apply aspect ratio adjustments only if not auto-centering
|
|
1126
|
+
if posX != -1 && posY != -1, let aspectRatio = self.aspectRatio {
|
|
1127
|
+
let ratioParts = aspectRatio.split(separator: ":").compactMap { Double($0) }
|
|
1128
|
+
if ratioParts.count == 2 {
|
|
1129
|
+
// For camera, use portrait orientation: 4:3 becomes 3:4, 16:9 becomes 9:16
|
|
1130
|
+
let ratio = ratioParts[1] / ratioParts[0]
|
|
1131
|
+
let currentRatio = Double(finalWidth) / Double(finalHeight)
|
|
1132
|
+
|
|
1133
|
+
if currentRatio > ratio {
|
|
1134
|
+
let newWidth = Double(finalHeight) * ratio
|
|
1135
|
+
frame.origin.x = finalX + (Double(finalWidth) - newWidth) / 2
|
|
1136
|
+
frame.size.width = CGFloat(newWidth)
|
|
1137
|
+
} else {
|
|
1138
|
+
let newHeight = Double(finalWidth) / ratio
|
|
1139
|
+
frame.origin.y = finalY + (Double(finalHeight) - newHeight) / 2
|
|
1140
|
+
frame.size.height = CGFloat(newHeight)
|
|
1141
|
+
}
|
|
1142
|
+
}
|
|
1143
|
+
}
|
|
1017
1144
|
|
|
1145
|
+
// Disable ALL animations for frame updates - we want instant positioning
|
|
1146
|
+
CATransaction.begin()
|
|
1147
|
+
CATransaction.setDisableActions(true)
|
|
1148
|
+
|
|
1149
|
+
// Batch UI updates for better performance
|
|
1018
1150
|
if self.previewView == nil {
|
|
1019
|
-
print("[CameraPreview] Creating new preview view with frame: \(frame)")
|
|
1020
1151
|
self.previewView = UIView(frame: frame)
|
|
1021
|
-
self.previewView.backgroundColor = UIColor.
|
|
1152
|
+
self.previewView.backgroundColor = UIColor.clear
|
|
1022
1153
|
} else {
|
|
1023
|
-
print("[CameraPreview] Updating existing preview view frame to: \(frame)")
|
|
1024
1154
|
self.previewView.frame = frame
|
|
1025
1155
|
}
|
|
1026
1156
|
|
|
1027
|
-
// Update
|
|
1028
|
-
self.cameraController.previewLayer
|
|
1029
|
-
|
|
1157
|
+
// Update preview layer frame efficiently
|
|
1158
|
+
if let previewLayer = self.cameraController.previewLayer {
|
|
1159
|
+
previewLayer.frame = self.previewView.bounds
|
|
1160
|
+
}
|
|
1161
|
+
|
|
1162
|
+
// Update grid overlay frame if it exists
|
|
1163
|
+
if let gridOverlay = self.cameraController.gridOverlayView {
|
|
1164
|
+
gridOverlay.frame = self.previewView.bounds
|
|
1165
|
+
}
|
|
1166
|
+
|
|
1167
|
+
CATransaction.commit()
|
|
1168
|
+
}
|
|
1169
|
+
|
|
1170
|
+
@objc func getPreviewSize(_ call: CAPPluginCall) {
|
|
1171
|
+
guard self.isInitialized else {
|
|
1172
|
+
call.reject("camera not started")
|
|
1173
|
+
return
|
|
1174
|
+
}
|
|
1175
|
+
var result = JSObject()
|
|
1176
|
+
result["x"] = Double(self.previewView.frame.origin.x)
|
|
1177
|
+
result["y"] = Double(self.previewView.frame.origin.y)
|
|
1178
|
+
result["width"] = Double(self.previewView.frame.width)
|
|
1179
|
+
result["height"] = Double(self.previewView.frame.height)
|
|
1180
|
+
call.resolve(result)
|
|
1181
|
+
}
|
|
1182
|
+
|
|
1183
|
+
@objc func setPreviewSize(_ call: CAPPluginCall) {
|
|
1184
|
+
guard self.isInitialized else {
|
|
1185
|
+
call.reject("camera not started")
|
|
1186
|
+
return
|
|
1187
|
+
}
|
|
1188
|
+
|
|
1189
|
+
// Only update position if explicitly provided, otherwise keep auto-centering
|
|
1190
|
+
if let x = call.getInt("x") {
|
|
1191
|
+
self.posX = CGFloat(x)
|
|
1192
|
+
}
|
|
1193
|
+
if let y = call.getInt("y") {
|
|
1194
|
+
self.posY = CGFloat(y)
|
|
1195
|
+
}
|
|
1196
|
+
if let width = call.getInt("width") { self.width = CGFloat(width) }
|
|
1197
|
+
if let height = call.getInt("height") { self.height = CGFloat(height) }
|
|
1198
|
+
|
|
1199
|
+
// Direct update without animation for better performance
|
|
1200
|
+
self.updateCameraFrame()
|
|
1201
|
+
self.makeWebViewTransparent()
|
|
1202
|
+
|
|
1203
|
+
// Return the actual preview bounds
|
|
1204
|
+
var result = JSObject()
|
|
1205
|
+
result["x"] = Double(self.previewView.frame.origin.x)
|
|
1206
|
+
result["y"] = Double(self.previewView.frame.origin.y)
|
|
1207
|
+
result["width"] = Double(self.previewView.frame.width)
|
|
1208
|
+
result["height"] = Double(self.previewView.frame.height)
|
|
1209
|
+
call.resolve(result)
|
|
1030
1210
|
}
|
|
1031
1211
|
}
|
package/package.json
CHANGED