diff --git a/example/CameraScreen.ios.js b/example/CameraScreen.ios.js
index 069f151..2c3d330 100644
--- a/example/CameraScreen.ios.js
+++ b/example/CameraScreen.ios.js
@@ -19,6 +19,8 @@ const FLASH_MODE_AUTO = "auto";
const FLASH_MODE_ON = "on";
const FLASH_MODE_OFF = "off";
+const RATIOS = ['3:4', '6:9', '1:1', '2:1'];
+
export default class CameraScreen extends Component {
constructor(props) {
@@ -31,7 +33,8 @@ export default class CameraScreen extends Component {
shouldOpenCamera: false,
shouldShowListView: false,
image:{imageURI:""},
- flashMode:FLASH_MODE_AUTO
+ flashMode:FLASH_MODE_AUTO,
+ ratiosArrayPosition: 0
}
}
render() {
@@ -49,11 +52,13 @@ export default class CameraScreen extends Component {
ref={(cam) => {
this.camera = cam;
}}
- style={{flex: 1}}
+ style={{flex: 1, backgroundColor:'white'}}
cameraOptions= {{
flashMode: 'auto', // on/off/auto(default)
focusMode: 'on', // off/on(default)
- zoomMode: 'on' // off/on(default)
+ zoomMode: 'on', // off/on(default)
+ ratioOverlay:RATIOS[this.state.ratiosArrayPosition],
+ ratioOverlayColor: '#00000077'
}}
/>
@@ -87,11 +92,19 @@ export default class CameraScreen extends Component {
+ this.ratioPressed() }>
+ {RATIOS[this.state.ratiosArrayPosition]}
+
+
)
}
+ ratioPressed() {
+ this.setState({ratiosArrayPosition: (this.state.ratiosArrayPosition+1)%(RATIOS.length)})
+ }
+
async onSwitchCameraPressed() {
const success = await this.camera.changeCamera();
}
diff --git a/ios/lib/ReactNativeCameraKit.xcodeproj/project.pbxproj b/ios/lib/ReactNativeCameraKit.xcodeproj/project.pbxproj
index 0e93320..ff273f6 100644
--- a/ios/lib/ReactNativeCameraKit.xcodeproj/project.pbxproj
+++ b/ios/lib/ReactNativeCameraKit.xcodeproj/project.pbxproj
@@ -13,6 +13,8 @@
26550AF61CFC7086007FF2DF /* CKCameraManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 26550AF51CFC7086007FF2DF /* CKCameraManager.m */; };
2685AA241CFD89A300E4A446 /* CKCamera.m in Sources */ = {isa = PBXBuildFile; fileRef = 2685AA231CFD89A300E4A446 /* CKCamera.m */; };
268A64B71D2BFE5A0034460B /* SelectionGesture.m in Sources */ = {isa = PBXBuildFile; fileRef = 268A64B61D2BFE5A0034460B /* SelectionGesture.m */; };
+ 269292831D3B7D6000E07DDF /* CKCameraOverlayView.m in Sources */ = {isa = PBXBuildFile; fileRef = 269292821D3B7D6000E07DDF /* CKCameraOverlayView.m */; };
+ 269292861D3B81C800E07DDF /* CKOverlayObject.m in Sources */ = {isa = PBXBuildFile; fileRef = 269292851D3B81C800E07DDF /* CKOverlayObject.m */; };
26F556721D2501C9007B1C11 /* GalleryData.m in Sources */ = {isa = PBXBuildFile; fileRef = 26F556711D2501C9007B1C11 /* GalleryData.m */; };
/* End PBXBuildFile section */
@@ -42,6 +44,10 @@
2685AA231CFD89A300E4A446 /* CKCamera.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = CKCamera.m; sourceTree = ""; };
268A64B51D2BFE5A0034460B /* SelectionGesture.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = SelectionGesture.h; sourceTree = ""; };
268A64B61D2BFE5A0034460B /* SelectionGesture.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = SelectionGesture.m; sourceTree = ""; };
+ 269292811D3B7D6000E07DDF /* CKCameraOverlayView.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = CKCameraOverlayView.h; sourceTree = ""; };
+ 269292821D3B7D6000E07DDF /* CKCameraOverlayView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = CKCameraOverlayView.m; sourceTree = ""; };
+ 269292841D3B81C800E07DDF /* CKOverlayObject.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = CKOverlayObject.h; sourceTree = ""; };
+ 269292851D3B81C800E07DDF /* CKOverlayObject.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = CKOverlayObject.m; sourceTree = ""; };
26F556701D2501C9007B1C11 /* GalleryData.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = GalleryData.h; sourceTree = ""; };
26F556711D2501C9007B1C11 /* GalleryData.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = GalleryData.m; sourceTree = ""; };
/* End PBXFileReference section */
@@ -90,6 +96,10 @@
26F556711D2501C9007B1C11 /* GalleryData.m */,
268A64B51D2BFE5A0034460B /* SelectionGesture.h */,
268A64B61D2BFE5A0034460B /* SelectionGesture.m */,
+ 269292811D3B7D6000E07DDF /* CKCameraOverlayView.h */,
+ 269292821D3B7D6000E07DDF /* CKCameraOverlayView.m */,
+ 269292841D3B81C800E07DDF /* CKOverlayObject.h */,
+ 269292851D3B81C800E07DDF /* CKOverlayObject.m */,
);
path = ReactNativeCameraKit;
sourceTree = "";
@@ -152,8 +162,10 @@
files = (
26550AF61CFC7086007FF2DF /* CKCameraManager.m in Sources */,
262E42201D183A6B00C82B27 /* CKGalleryCollectionViewCell.m in Sources */,
+ 269292861D3B81C800E07DDF /* CKOverlayObject.m in Sources */,
26550AE61CFC2437007FF2DF /* CKGalleryManager.m in Sources */,
2685AA241CFD89A300E4A446 /* CKCamera.m in Sources */,
+ 269292831D3B7D6000E07DDF /* CKCameraOverlayView.m in Sources */,
26F556721D2501C9007B1C11 /* GalleryData.m in Sources */,
268A64B71D2BFE5A0034460B /* SelectionGesture.m in Sources */,
262E421D1D182C1200C82B27 /* CKGalleryViewManager.m in Sources */,
diff --git a/ios/lib/ReactNativeCameraKit/CKCamera.h b/ios/lib/ReactNativeCameraKit/CKCamera.h
index 59e6c5a..9b17a5e 100644
--- a/ios/lib/ReactNativeCameraKit/CKCamera.h
+++ b/ios/lib/ReactNativeCameraKit/CKCamera.h
@@ -58,5 +58,6 @@ typedef NS_ENUM(NSInteger, CKCameraZoomMode) {
- (void)snapStillImage:(BOOL)shouldSaveToCameraRoll success:(CaptureBlock)block;
- (void)changeCamera:(CallbackBlock)block;
- (void)setFlashMode:(AVCaptureFlashMode)flashMode callback:(CallbackBlock)block;
+- (void)setRatio:(NSString*)ratioString;
@end
diff --git a/ios/lib/ReactNativeCameraKit/CKCamera.m b/ios/lib/ReactNativeCameraKit/CKCamera.m
index 885464f..fddab0c 100644
--- a/ios/lib/ReactNativeCameraKit/CKCamera.m
+++ b/ios/lib/ReactNativeCameraKit/CKCamera.m
@@ -11,6 +11,7 @@
#import "CKCamera.h"
#import "UIView+React.h"
#import "RCTConvert.h"
+#import "CKCameraOverlayView.h"
static void * CapturingStillImageContext = &CapturingStillImageContext;
@@ -52,9 +53,11 @@ RCT_ENUM_CONVERTER(CKCameraZoomMode, (@{
-#define CAMERA_OPTION_FLASH_MODE @"flashMode"
-#define CAMERA_OPTION_FOCUS_MODE @"focusMode"
-#define CAMERA_OPTION_ZOOM_MODE @"zoomMode"
+#define CAMERA_OPTION_FLASH_MODE @"flashMode"
+#define CAMERA_OPTION_FOCUS_MODE @"focusMode"
+#define CAMERA_OPTION_ZOOM_MODE @"zoomMode"
+#define CAMERA_OPTION_CAMERA_RATIO_OVERLAY @"ratioOverlay"
+#define CAMERA_OPTION_CAMERA_RATIO_OVERLAY_COLOR @"ratioOverlayColor"
#define TIMER_FOCUS_TIME_SECONDS 5
@interface CKCamera ()
@@ -64,6 +67,7 @@ RCT_ENUM_CONVERTER(CKCameraZoomMode, (@{
@property (nonatomic, strong) NSDictionary *cameraOptions;
@property (nonatomic, strong) UIView *focusView;
@property (nonatomic, strong) NSTimer *focusViewTimer;
+@property (nonatomic, strong) CKCameraOverlayView *cameraOverlayView;
// session management
@property (nonatomic) dispatch_queue_t sessionQueue;
@@ -82,6 +86,8 @@ RCT_ENUM_CONVERTER(CKCameraZoomMode, (@{
@property (nonatomic) CKCameraFocushMode focusMode;
@property (nonatomic) CKCameraZoomMode zoomMode;
@property (nonatomic, strong) PHFetchOptions *fetchOptions;
+@property (nonatomic, strong) NSString* ratioOverlayString;
+@property (nonatomic, strong) UIColor *ratioOverlayColor;
@property (nonatomic) BOOL isAddedOberver;
@@ -118,18 +124,14 @@ RCT_ENUM_CONVERTER(CKCameraZoomMode, (@{
- (void)removeFromSuperview
{
-
+ [super removeFromSuperview];
dispatch_async( self.sessionQueue, ^{
if ( self.setupResult == CKSetupResultSuccess ) {
[self.session stopRunning];
[self removeObservers];
}
-
} );
- [super removeFromSuperview];
-
-
}
- (instancetype)initWithFrame:(CGRect)frame {
@@ -198,6 +200,19 @@ RCT_ENUM_CONVERTER(CKCameraZoomMode, (@{
[self addGestureRecognizer:pinchGesture];
}
}
+
+ // CAMERA_OPTION_CAMERA_RATIO_OVERLAY_COLOR
+ id ratioOverlayColor = self.cameraOptions[CAMERA_OPTION_CAMERA_RATIO_OVERLAY_COLOR];
+ if (ratioOverlayColor) {
+ self.ratioOverlayColor = [RCTConvert UIColor:ratioOverlayColor];
+ }
+
+ // CAMERA_OPTION_CAMERA_RATIO_OVERLAY
+ id ratioOverlay = self.cameraOptions[CAMERA_OPTION_CAMERA_RATIO_OVERLAY];
+ if (ratioOverlay) {
+ self.ratioOverlayString = [RCTConvert NSString:ratioOverlay];
+ [self setRatio:self.ratioOverlayString];
+ }
}
@@ -300,6 +315,7 @@ RCT_ENUM_CONVERTER(CKCameraZoomMode, (@{
[super reactSetFrame:frame];
self.previewLayer.frame = self.bounds;
+ [self setOverlayRatioView];
dispatch_async( self.sessionQueue, ^{
switch ( self.setupResult )
@@ -343,6 +359,18 @@ RCT_ENUM_CONVERTER(CKCameraZoomMode, (@{
} );
}
+-(void)setRatioOverlayString:(NSString *)ratioOverlayString {
+ _ratioOverlayString = ratioOverlayString;
+ [self.cameraOverlayView setRatio:self.ratioOverlayString];
+}
+
+-(void)setOverlayRatioView {
+ if (!self.cameraOverlayView) {
+ self.cameraOverlayView = [[CKCameraOverlayView alloc] initWithFrame:self.bounds ratioString:self.ratioOverlayString overlayColor:self.ratioOverlayColor];
+ [self addSubview:self.cameraOverlayView];
+ }
+}
+
#pragma mark -
@@ -385,6 +413,7 @@ RCT_ENUM_CONVERTER(CKCameraZoomMode, (@{
captureDevice = device;
break;
}
+
}
return captureDevice;
@@ -413,6 +442,12 @@ RCT_ENUM_CONVERTER(CKCameraZoomMode, (@{
}
}
+- (void)setRatio:(NSString*)ratioString {
+ if (ratioString && ![ratioString isEqualToString:@""]) {
+ self.ratioOverlayString = ratioString;
+ }
+}
+
#pragma mark - actions
@@ -425,14 +460,27 @@ RCT_ENUM_CONVERTER(CKCameraZoomMode, (@{
// Update the orientation on the still image output video connection before capturing.
connection.videoOrientation = self.previewLayer.connection.videoOrientation;
- // Flash set to Auto for Still Capture.
- // [CKCamera setFlashMode:AVCaptureFlashModeAuto forDevice:self.videoDeviceInput.device];
// Capture a still image.
[self.stillImageOutput captureStillImageAsynchronouslyFromConnection:connection completionHandler:^( CMSampleBufferRef imageDataSampleBuffer, NSError *error ) {
if ( imageDataSampleBuffer ) {
// The sample buffer is not retained. Create image data before saving the still image to the photo library asynchronously.
NSData *imageData = [AVCaptureStillImageOutput jpegStillImageNSDataRepresentation:imageDataSampleBuffer];
+ UIImage *capturedImage = [UIImage imageWithData:imageData];
+ capturedImage = [CKCamera rotateImage:capturedImage];
+
+ CGSize previewScaleSize = [CKCamera cropImageToPreviewSize:capturedImage size:self.previewLayer.bounds.size];
+ CGRect rectToCrop = CGRectMake((capturedImage.size.width-previewScaleSize.width)*0.5, (capturedImage.size.height-previewScaleSize.height)*0.5, previewScaleSize.width, previewScaleSize.height);
+
+ if (self.ratioOverlayString) {
+
+ rectToCrop = [CKCamera cropRectForSize:rectToCrop overlayObject:self.cameraOverlayView.overlayObject];
+ }
+
+ CGImageRef imageRef = CGImageCreateWithImageInRect(capturedImage.CGImage, rectToCrop);
+ capturedImage = [UIImage imageWithCGImage:imageRef scale:capturedImage.scale orientation:UIImageOrientationUp];
+ imageData = UIImageJPEGRepresentation(capturedImage, capturedImage.scale); // TODO: check JPEG representation
+
[PHPhotoLibrary requestAuthorization:^( PHAuthorizationStatus status ) {
if ( status == PHAuthorizationStatusAuthorized ) {
@@ -450,7 +498,7 @@ RCT_ENUM_CONVERTER(CKCameraZoomMode, (@{
if (success) {
PHFetchResult *fetchResult = [PHAsset fetchAssetsWithMediaType:PHAssetMediaTypeImage options:self.fetchOptions];
- PHAsset *lastImageAsset = [fetchResult firstObject];
+ PHAsset *lastImageAsset = [fetchResult lastObject];
if (lastImageAsset.localIdentifier) {
imageInfoDict[@"id"] = lastImageAsset.localIdentifier;
@@ -481,6 +529,22 @@ RCT_ENUM_CONVERTER(CKCameraZoomMode, (@{
} );
}
++(UIImage*)rotateImage:(UIImage*)originalImage {
+
+ if (originalImage.imageOrientation == UIImageOrientationUp || originalImage == nil)
+ return originalImage;
+
+
+ UIGraphicsBeginImageContextWithOptions(originalImage.size, NO, originalImage.scale);
+
+ [originalImage drawInRect:(CGRect){0, 0, originalImage.size}];
+ UIImage *normalizedImage = UIGraphicsGetImageFromCurrentImageContext();
+
+ UIGraphicsEndImageContext();
+
+ return normalizedImage;
+}
+
-(void)changeCamera:(CallbackBlock)block
{
@@ -643,7 +707,6 @@ RCT_ENUM_CONVERTER(CKCameraZoomMode, (@{
}
-
- (void)focusWithMode:(AVCaptureFocusMode)focusMode exposeWithMode:(AVCaptureExposureMode)exposureMode atDevicePoint:(CGPoint)point monitorSubjectAreaChange:(BOOL)monitorSubjectAreaChange
{
dispatch_async( self.sessionQueue, ^{
@@ -695,6 +758,64 @@ RCT_ENUM_CONVERTER(CKCameraZoomMode, (@{
}
++ (UIImage *)imageWithImage:(UIImage *)image scaledToRect:(CGSize)newSize {
+ //UIGraphicsBeginImageContext(newSize);
+ // In next line, pass 0.0 to use the current device's pixel scaling factor (and thus account for Retina resolution).
+ // Pass 1.0 to force exact pixel size.
+ UIGraphicsBeginImageContextWithOptions(newSize, NO, 0.0);
+ [image drawInRect:CGRectMake(0, 0, newSize.width, newSize.height)];
+ UIImage *newImage = UIGraphicsGetImageFromCurrentImageContext();
+ UIGraphicsEndImageContext();
+ return newImage;
+}
+
+
++(CGRect)cropRectForSize:(CGRect)frame overlayObject:(CKOverlayObject*)overlayObject {
+
+ CGRect ans = CGRectZero;
+ CGSize centerSize = CGSizeZero;
+
+ if (overlayObject.width < overlayObject.height) {
+ centerSize.width = frame.size.width;
+ centerSize.height = frame.size.height * overlayObject.ratio;
+
+ ans.origin.x = 0;
+ ans.origin.y = (frame.size.height - centerSize.height)*0.5;
+
+ }
+ else if (overlayObject.width > overlayObject.height){
+ centerSize.width = frame.size.width / overlayObject.ratio;
+ centerSize.height = frame.size.height;
+
+ ans.origin.x = (frame.size.width - centerSize.width)*0.5;
+ ans.origin.y = 0;
+
+ }
+ else { // ratio is 1:1
+ centerSize.width = frame.size.width;
+ centerSize.height = frame.size.width;
+
+ ans.origin.x = 0;
+ ans.origin.y = (frame.size.height - centerSize.height)/2;
+ }
+
+ ans.size = centerSize;
+ ans.origin.x += frame.origin.x;
+ ans.origin.y += frame.origin.y;
+ return ans;
+}
+
++(CGSize)cropImageToPreviewSize:(UIImage*)image size:(CGSize)previewSize {
+
+ CGRect ans = CGRectZero;
+ CGSize centerSize = CGSizeZero;
+
+ float imageToPreviewWidthScale = image.size.width/previewSize.width;
+ float imageToPreviewHeightScale = image.size.width/previewSize.width;
+
+ return CGSizeMake(previewSize.width*imageToPreviewWidthScale, previewSize.height*imageToPreviewHeightScale);
+}
+
#pragma mark - observers
@@ -713,7 +834,6 @@ RCT_ENUM_CONVERTER(CKCameraZoomMode, (@{
// and show a preview is paused message. See the documentation of AVCaptureSessionWasInterruptedNotification for other
// interruption reasons.
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(sessionWasInterrupted:) name:AVCaptureSessionWasInterruptedNotification object:self.session];
- [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(sessionInterruptionEnded:) name:AVCaptureSessionInterruptionEndedNotification object:self.session];
self.isAddedOberver = YES;
}
}
@@ -737,48 +857,7 @@ RCT_ENUM_CONVERTER(CKCameraZoomMode, (@{
reason == AVCaptureSessionInterruptionReasonVideoDeviceInUseByAnotherClient ) {
showResumeButton = YES;
}
- // else if ( reason == AVCaptureSessionInterruptionReasonVideoDeviceNotAvailableWithMultipleForegroundApps ) {
- // // Simply fade-in a label to inform the user that the camera is unavailable.
- // self.cameraUnavailableLabel.hidden = NO;
- // self.cameraUnavailableLabel.alpha = 0.0;
- // [UIView animateWithDuration:0.25 animations:^{
- // self.cameraUnavailableLabel.alpha = 1.0;
- // }];
- // }
}
- else {
- //NSLog( @"Capture session was interrupted" );
- showResumeButton = ( [UIApplication sharedApplication].applicationState == UIApplicationStateInactive );
- }
-
- // if ( showResumeButton ) {
- // // Simply fade-in a button to enable the user to try to resume the session running.
- // self.resumeButton.hidden = NO;
- // self.resumeButton.alpha = 0.0;
- // [UIView animateWithDuration:0.25 animations:^{
- // self.resumeButton.alpha = 1.0;
- // }];
- // }
-}
-
-- (void)sessionInterruptionEnded:(NSNotification *)notification
-{
- //NSLog( @"Capture session interruption ended" );
-
- // if ( ! self.resumeButton.hidden ) {
- // [UIView animateWithDuration:0.25 animations:^{
- // self.resumeButton.alpha = 0.0;
- // } completion:^( BOOL finished ) {
- // self.resumeButton.hidden = YES;
- // }];
- // }
- // if ( ! self.cameraUnavailableLabel.hidden ) {
- // [UIView animateWithDuration:0.25 animations:^{
- // self.cameraUnavailableLabel.alpha = 0.0;
- // } completion:^( BOOL finished ) {
- // self.cameraUnavailableLabel.hidden = YES;
- // }];
- // }
}
diff --git a/ios/lib/ReactNativeCameraKit/CKCameraManager.m b/ios/lib/ReactNativeCameraKit/CKCameraManager.m
index 3cd92ff..ef5205c 100644
--- a/ios/lib/ReactNativeCameraKit/CKCameraManager.m
+++ b/ios/lib/ReactNativeCameraKit/CKCameraManager.m
@@ -27,7 +27,7 @@ RCT_EXPORT_MODULE()
return self.camera;
}
-RCT_REMAP_VIEW_PROPERTY(cameraOptions, cameraOptions, NSDictionary)
+RCT_EXPORT_VIEW_PROPERTY(cameraOptions, NSDictionary)
RCT_EXPORT_METHOD(checkDeviceAuthorizationStatus:(RCTPromiseResolveBlock)resolve
diff --git a/ios/lib/ReactNativeCameraKit/CKCameraOverlayView.h b/ios/lib/ReactNativeCameraKit/CKCameraOverlayView.h
new file mode 100644
index 0000000..40c8f51
--- /dev/null
+++ b/ios/lib/ReactNativeCameraKit/CKCameraOverlayView.h
@@ -0,0 +1,26 @@
+//
+// CKCameraOverlayView.h
+// ReactNativeCameraKit
+//
+// Created by Ran Greenberg on 17/07/2016.
+// Copyright © 2016 Wix. All rights reserved.
+//
+
+#import
+#import "CKOverlayObject.h"
+
+@interface CKCameraOverlayView : UIView
+
+
+@property (nonatomic, strong, readonly) UIView *centerView;
+@property (nonatomic, strong, readonly) CKOverlayObject *overlayObject;
+
+
+
+-(instancetype)initWithFrame:(CGRect)frame ratioString:(NSString*)ratioString overlayColor:(UIColor*)overlayColor;
+
+-(void)setRatio:(NSString*)ratioString;
+
+
+
+@end
diff --git a/ios/lib/ReactNativeCameraKit/CKCameraOverlayView.m b/ios/lib/ReactNativeCameraKit/CKCameraOverlayView.m
new file mode 100644
index 0000000..4820876
--- /dev/null
+++ b/ios/lib/ReactNativeCameraKit/CKCameraOverlayView.m
@@ -0,0 +1,109 @@
+//
+// CKCameraOverlayView.m
+// ReactNativeCameraKit
+//
+// Created by Ran Greenberg on 17/07/2016.
+// Copyright © 2016 Wix. All rights reserved.
+//
+
+#import "CKCameraOverlayView.h"
+
+
+
+@interface CKCameraOverlayView ()
+
+@property (nonatomic, strong, readwrite) CKOverlayObject *overlayObject;
+@property (nonatomic, strong) UIView *topView;
+@property (nonatomic, strong, readwrite) UIView *centerView;
+@property (nonatomic, strong) UIView *bottomView;
+
+
+@end
+
+@implementation CKCameraOverlayView
+
+
+
+-(instancetype)initWithFrame:(CGRect)frame ratioString:(NSString*)ratioString overlayColor:(UIColor*)overlayColor {
+
+ self = [super initWithFrame:frame];
+
+ if (self) {
+
+ self.overlayObject = [[CKOverlayObject alloc] initWithString:ratioString];
+ self.topView = [[UIView alloc] initWithFrame:CGRectZero];
+ self.centerView = [[UIView alloc] initWithFrame:CGRectZero];
+ self.bottomView = [[UIView alloc] initWithFrame:CGRectZero];
+
+ overlayColor = overlayColor ? overlayColor : [UIColor colorWithRed:0 green:0 blue:0 alpha:0.3];
+
+ self.topView.backgroundColor = overlayColor;
+ self.bottomView.backgroundColor = overlayColor;
+
+ [self addSubview:self.topView];
+ [self addSubview:self.centerView];
+ [self addSubview:self.bottomView];
+
+ [self setOverlayParts];
+ }
+
+ return self;
+}
+
+
+-(void)setOverlayParts {
+
+ if (self.overlayObject.ratio == 0) return;
+
+ CGSize centerSize = CGSizeZero;
+ CGSize sideSize = CGSizeZero;
+
+ if (self.overlayObject.width < self.overlayObject.height) {
+
+ centerSize.width = self.frame.size.width;
+ centerSize.height = self.frame.size.height * self.overlayObject.ratio;
+
+ sideSize.width = centerSize.width;
+ sideSize.height = (self.frame.size.height - centerSize.height)/2.0;
+
+ self.topView.frame = CGRectMake(0, 0, sideSize.width, sideSize.height);
+ self.centerView.frame = CGRectMake(0, self.topView.frame.size.height + self.topView.frame.origin.y, centerSize.width, centerSize.height);
+ self.bottomView.frame = CGRectMake(0, self.centerView.frame.size.height + self.centerView.frame.origin.y, sideSize.width, sideSize.height);
+ }
+ else if (self.overlayObject.width > self.overlayObject.height){
+ centerSize.width = self.frame.size.width / self.overlayObject.ratio;
+ centerSize.height = self.frame.size.height;
+
+ sideSize.width = (self.frame.size.width - centerSize.width)/2.0;
+ sideSize.height = centerSize.height;
+
+ self.topView.frame = CGRectMake(0, 0, sideSize.width, sideSize.height);
+ self.centerView.frame = CGRectMake(self.topView.frame.size.width + self.topView.frame.origin.x, 0, centerSize.width, centerSize.height);
+ self.bottomView.frame = CGRectMake(self.centerView.frame.size.width + self.centerView.frame.origin.x, 0, sideSize.width, sideSize.height);
+ }
+ else { // ratio is 1:1
+ centerSize.width = self.frame.size.width;
+ centerSize.height = self.frame.size.width;
+
+ sideSize.width = centerSize.width;
+ sideSize.height = (self.frame.size.height - centerSize.height)/2.0;
+
+ self.topView.frame = CGRectMake(0, 0, sideSize.width, sideSize.height);
+ self.centerView.frame = CGRectMake(0, self.topView.frame.size.height + self.topView.frame.origin.y, centerSize.width, centerSize.height);
+ self.bottomView.frame = CGRectMake(0, self.centerView.frame.size.height + self.centerView.frame.origin.y, sideSize.width, sideSize.height);
+ }
+}
+
+
+-(void)setRatio:(NSString*)ratioString {
+ self.overlayObject = [[CKOverlayObject alloc] initWithString:ratioString];
+
+// self.alpha =0;
+ [UIView animateWithDuration:0.2 animations:^{
+ [self setOverlayParts];
+ } completion:nil];
+
+}
+
+
+@end
diff --git a/ios/lib/ReactNativeCameraKit/CKOverlayObject.h b/ios/lib/ReactNativeCameraKit/CKOverlayObject.h
new file mode 100644
index 0000000..baafeaf
--- /dev/null
+++ b/ios/lib/ReactNativeCameraKit/CKOverlayObject.h
@@ -0,0 +1,21 @@
+//
+// CKOverlayObject.h
+// ReactNativeCameraKit
+//
+// Created by Ran Greenberg on 17/07/2016.
+// Copyright © 2016 Wix. All rights reserved.
+//
+
+#import
+
+@interface CKOverlayObject : NSObject
+
+
+@property (nonatomic, readonly) float width;
+@property (nonatomic, readonly) float height;
+@property (nonatomic, readonly) float ratio;
+
+-(instancetype)initWithString:(NSString*)str;
+
+
+@end
diff --git a/ios/lib/ReactNativeCameraKit/CKOverlayObject.m b/ios/lib/ReactNativeCameraKit/CKOverlayObject.m
new file mode 100644
index 0000000..da20a6c
--- /dev/null
+++ b/ios/lib/ReactNativeCameraKit/CKOverlayObject.m
@@ -0,0 +1,52 @@
+//
+// CKOverlayObject.m
+// ReactNativeCameraKit
+//
+// Created by Ran Greenberg on 17/07/2016.
+// Copyright © 2016 Wix. All rights reserved.
+//
+
+#import "CKOverlayObject.h"
+
+@interface CKOverlayObject ()
+
+@property (nonatomic, readwrite) float width;
+@property (nonatomic, readwrite) float height;
+@property (nonatomic, readwrite) float ratio;
+
+@end
+
+@implementation CKOverlayObject
+
+-(instancetype)initWithString:(NSString*)str {
+
+ self = [super init];
+
+ if (self) {
+ [self commonInit:str];
+ }
+
+ return self;
+}
+
+-(void)commonInit:(NSString*)str {
+
+ NSArray *array = [str componentsSeparatedByString:@":"];
+ if (array.count == 2) {
+ float first = [array[0] floatValue];
+ float second = [array[1] floatValue];
+
+ if (first != 0 && second != 0) {
+ self.width = first;
+ self.height = second;
+ self.ratio = self.width/self.height;
+ }
+ }
+}
+
+-(NSString *)description {
+ return [NSString stringWithFormat:@"width:%f height:%f ratio:%f", self.width, self.height, self.ratio];
+}
+
+
+@end
diff --git a/src/CameraKitCamera.ios.js b/src/CameraKitCamera.ios.js
index c98c3e5..bd30316 100644
--- a/src/CameraKitCamera.ios.js
+++ b/src/CameraKitCamera.ios.js
@@ -1,7 +1,9 @@
+import _ from 'lodash';
import React, {Component} from 'react';
import {
requireNativeComponent,
- NativeModules
+ NativeModules,
+ processColor
} from 'react-native';
const NativeCamera = requireNativeComponent('CKCamera', null);
@@ -9,6 +11,10 @@ const NativeCameraAction = NativeModules.CKCameraManager;
export default class CameraKitCamera extends React.Component {
render() {
+
+ const transformedProps = {...this.props};
+ _.update(transformedProps, 'cameraOptions.ratioOverlayColor', (c) => processColor(c));
+
return
}