diff --git a/LICENSE.md b/LICENSE.md new file mode 100644 index 0000000..c15c920 --- /dev/null +++ b/LICENSE.md @@ -0,0 +1,13 @@ +Copyright 2016 Woon Tien Jing + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. diff --git a/README.md b/README.md index 27cc2bc..474f3b2 100644 --- a/README.md +++ b/README.md @@ -1,17 +1,18 @@ +**This repository is looking for a maintainer! If you believe you are the right person, please [leave a comment](https://github.com/tjwoon/csZBar/issues/60)!** + + + # ZBar Barcode Scanner Plugin :warning: This plugin is SUPPORTED by OutSystems. Customers entitled to Support Services may obtain assistance through Support. This plugin integrates with the [ZBar](http://zbar.sourceforge.net/) library, exposing a JavaScript interface for scanning barcodes (QR, 2D, etc). +In this fork a button has been added to turn off and on device flash. In addition the plugin can now handle the device orientation change. ## Installation - cordova plugins add org.cloudsky.cordovaplugins.zbar - -## License - -This plugin is released under the Apache 2.0 license, but the ZBar library on which it depends (and which is distribute with this plugin) is under the LGPL license (2.1). + cordova plugin add cordova-plugin-cszbar ## API @@ -47,11 +48,10 @@ Status: - Android: DONE - iOS: DONE -Quirks: -- __Android__: On Android API Level < 14, flash "on" may cause the flash to - alternate between on and off at about a half second/one second interval, - instead of making it stay on... +## LICENSE [Apache 2.0](LICENSE.md) + +This plugin is released under the Apache 2.0 license, but the ZBar library on which it depends (and which is distribute with this plugin) is under the LGPL license (2.1). ## Thanks diff --git a/android/ZBarScannerActivity.java b/android/ZBarScannerActivity.java index 1490aeb..9f23fa2 100644 --- a/android/ZBarScannerActivity.java +++ b/android/ZBarScannerActivity.java @@ -5,15 +5,20 @@ import org.json.JSONException; import org.json.JSONObject; +import android.Manifest; import android.app.Activity; import android.content.Intent; +import android.content.res.Configuration; import android.content.res.Resources; import android.hardware.Camera; import android.hardware.Camera.CameraInfo; +import android.hardware.Camera.Parameters; import android.hardware.Camera.PreviewCallback; import android.hardware.Camera.AutoFocusCallback; import android.os.Bundle; import android.os.Handler; +import android.support.v4.app.ActivityCompat; +import android.support.v4.content.ContextCompat; import android.util.Log; import android.view.Gravity; import android.view.SurfaceHolder; @@ -22,6 +27,9 @@ import android.view.ViewGroup; import android.widget.FrameLayout; import android.widget.TextView; +import android.content.pm.PackageManager; +import android.view.Surface; + import java.util.ArrayList; import java.util.Collection; @@ -43,14 +51,14 @@ public class ZBarScannerActivity extends Activity // Config ---------------------------------------------------------- - private static int autoFocusInterval = 500; // Interval between AFcallback and next AF attempt. + private static int autoFocusInterval = 2000; // Interval between AFcallback and next AF attempt. // Public Constants ------------------------------------------------ public static final String EXTRA_QRVALUE = "qrValue"; public static final String EXTRA_PARAMS = "params"; public static final int RESULT_ERROR = RESULT_FIRST_USER + 1; - + private static final int CAMERA_PERMISSION_REQUEST = 1; // State ----------------------------------------------------------- private Camera camera; @@ -80,73 +88,111 @@ public class ZBarScannerActivity extends Activity // Activity Lifecycle ---------------------------------------------- @Override - public void onCreate (Bundle savedInstanceState) - { - super.onCreate(savedInstanceState); + public void onCreate (Bundle savedInstanceState) { + + + int permissionCheck = ContextCompat.checkSelfPermission(this.getBaseContext(), Manifest.permission.CAMERA); + + if(permissionCheck == PackageManager.PERMISSION_GRANTED){ - // Get parameters from JS - Intent startIntent = getIntent(); - String paramStr = startIntent.getStringExtra(EXTRA_PARAMS); - JSONObject params; - try { params = new JSONObject(paramStr); } - catch (JSONException e) { params = new JSONObject(); } - String textTitle = params.optString("text_title"); - String textInstructions = params.optString("text_instructions"); - Boolean drawSight = params.optBoolean("drawSight", true); - whichCamera = params.optString("camera"); - flashMode = params.optString("flash"); - - // Initiate instance variables - autoFocusHandler = new Handler(); - scanner = new ImageScanner(); - scanner.setConfig(0, Config.X_DENSITY, 3); - scanner.setConfig(0, Config.Y_DENSITY, 3); - - // Set the config for barcode formats - for(ZBarcodeFormat format : getFormats()) { - scanner.setConfig(format.getId(), Config.ENABLE, 1); + setUpCamera(); + + } else { + + ActivityCompat.requestPermissions(this, + new String[]{Manifest.permission.CAMERA}, + CAMERA_PERMISSION_REQUEST); } + super.onCreate(savedInstanceState); - // Set content view - setContentView(getResourceId("layout/cszbarscanner")); - // Update view with customisable strings - TextView view_textTitle = (TextView) findViewById(getResourceId("id/csZbarScannerTitle")); - TextView view_textInstructions = (TextView) findViewById(getResourceId("id/csZbarScannerInstructions")); - view_textTitle.setText(textTitle); - view_textInstructions.setText(textInstructions); + } + public void onRequestPermissionsResult(int requestCode, + String permissions[], int[] grantResults) { + switch (requestCode) { + case CAMERA_PERMISSION_REQUEST: { + if (grantResults.length > 0 + && grantResults[0] == PackageManager.PERMISSION_GRANTED) { + setUpCamera(); + } else { + + onBackPressed(); + } + return; + } - // Draw/hide the sight - if(!drawSight) { - findViewById(getResourceId("id/csZbarScannerSight")).setVisibility(View.INVISIBLE); + // other 'case' lines to check for other + // permissions this app might request } + } + private void setUpCamera() { + // If request is cancelled, the result arrays are empty. + + + // Get parameters from JS + Intent startIntent = getIntent(); + String paramStr = startIntent.getStringExtra(EXTRA_PARAMS); + JSONObject params; + try { params = new JSONObject(paramStr); } + catch (JSONException e) { params = new JSONObject(); } + String textTitle = params.optString("text_title"); + String textInstructions = params.optString("text_instructions"); + Boolean drawSight = params.optBoolean("drawSight", true); + whichCamera = params.optString("camera"); + flashMode = params.optString("flash"); + + // Initiate instance variables + autoFocusHandler = new Handler(); + scanner = new ImageScanner(); + scanner.setConfig(0, Config.X_DENSITY, 3); + scanner.setConfig(0, Config.Y_DENSITY, 3); + + // Set the config for barcode formats + for(ZBarcodeFormat format : getFormats()) { + scanner.setConfig(format.getId(), Config.ENABLE, 1); + } - // Create preview SurfaceView - scannerSurface = new SurfaceView (this) { - @Override - public void onSizeChanged (int w, int h, int oldW, int oldH) { - surfW = w; - surfH = h; - matchSurfaceToPreviewRatio(); + // Set content view + setContentView(getResourceId("layout/cszbarscanner")); + + // Update view with customisable strings + TextView view_textTitle = (TextView) findViewById(getResourceId("id/csZbarScannerTitle")); + TextView view_textInstructions = (TextView) findViewById(getResourceId("id/csZbarScannerInstructions")); + view_textTitle.setText(textTitle); + view_textInstructions.setText(textInstructions); + + // Draw/hide the sight + if(!drawSight) { + findViewById(getResourceId("id/csZbarScannerSight")).setVisibility(View.INVISIBLE); } - }; - scannerSurface.setLayoutParams(new FrameLayout.LayoutParams( - ViewGroup.LayoutParams.MATCH_PARENT, - ViewGroup.LayoutParams.MATCH_PARENT, - Gravity.CENTER - )); - scannerSurface.getHolder().addCallback(this); - - // Add preview SurfaceView to the screen - FrameLayout scannerView = (FrameLayout) findViewById(getResourceId("id/csZbarScannerView")); - scannerView.addView(scannerSurface); - - findViewById(getResourceId("id/csZbarScannerTitle")).bringToFront(); - findViewById(getResourceId("id/csZbarScannerInstructions")).bringToFront(); - findViewById(getResourceId("id/csZbarScannerSightContainer")).bringToFront(); - findViewById(getResourceId("id/csZbarScannerSight")).bringToFront(); - scannerView.requestLayout(); - scannerView.invalidate(); + + // Create preview SurfaceView + scannerSurface = new SurfaceView (this) { + @Override + public void onSizeChanged (int w, int h, int oldW, int oldH) { + surfW = w; + surfH = h; + matchSurfaceToPreviewRatio(); + } + }; + scannerSurface.setLayoutParams(new FrameLayout.LayoutParams( + ViewGroup.LayoutParams.MATCH_PARENT, + ViewGroup.LayoutParams.MATCH_PARENT, + Gravity.CENTER + )); + scannerSurface.getHolder().addCallback(this); + + // Add preview SurfaceView to the screen + FrameLayout scannerView = (FrameLayout) findViewById(getResourceId("id/csZbarScannerView")); + scannerView.addView(scannerSurface); + + findViewById(getResourceId("id/csZbarScannerTitle")).bringToFront(); + findViewById(getResourceId("id/csZbarScannerInstructions")).bringToFront(); + findViewById(getResourceId("id/csZbarScannerSightContainer")).bringToFront(); + findViewById(getResourceId("id/csZbarScannerSight")).bringToFront(); + scannerView.requestLayout(); + scannerView.invalidate(); + } @Override @@ -170,33 +216,36 @@ public void onResume () if(camera == null) throw new Exception ("Error: No suitable camera found."); } catch (RuntimeException e) { - die("Error: Could not open the camera."); + //die("Error: Could not open the camera."); return; } catch (Exception e) { - die(e.getMessage()); + // die(e.getMessage()); return; } - - Camera.Parameters camParams = camera.getParameters(); - if(flashMode.equals("on")) { - camParams.setFlashMode(Camera.Parameters.FLASH_MODE_ON); - } else if(flashMode.equals("off")) { - camParams.setFlashMode(Camera.Parameters.FLASH_MODE_OFF); - } else { - camParams.setFlashMode(Camera.Parameters.FLASH_MODE_AUTO); - } - if (android.os.Build.VERSION.SDK_INT >= 14) { - camParams.setFocusMode(Camera.Parameters.FOCUS_MODE_CONTINUOUS_PICTURE); + } + private void setCameraDisplayOrientation(Activity activity ,int cameraId) { + android.hardware.Camera.CameraInfo info = + new android.hardware.Camera.CameraInfo(); + android.hardware.Camera.getCameraInfo(cameraId, info); + int rotation = activity.getWindowManager().getDefaultDisplay() + .getRotation(); + int degrees = 0; + switch (rotation) { + case Surface.ROTATION_0: degrees = 0; break; + case Surface.ROTATION_90: degrees = 90; break; + case Surface.ROTATION_180: degrees = 180; break; + case Surface.ROTATION_270: degrees = 270; break; } - try { camera.setParameters(camParams); } - catch (RuntimeException e) { - Log.d("csZBar", "Unsupported camera parameter reported for flash mode: "+flashMode); + int result; + if (info.facing == Camera.CameraInfo.CAMERA_FACING_FRONT) { + result = (info.orientation + degrees) % 360; + result = (360 - result) % 360; // compensate the mirror + } else { // back-facing + result = (info.orientation - degrees + 360) % 360; } - - tryStartPreview(); + camera.setDisplayOrientation(result); } - @Override public void onPause () { @@ -207,7 +256,7 @@ public void onPause () @Override public void onDestroy () { - scanner.destroy(); + if(scanner != null) scanner.destroy(); super.onDestroy(); } @@ -251,7 +300,75 @@ public void surfaceChanged (SurfaceHolder hld, int fmt, int w, int h) holder = hld; tryStartPreview(); } + public void onConfigurationChanged(Configuration newConfig) + { + super.onConfigurationChanged(newConfig); + int rotation = getWindowManager().getDefaultDisplay().getRotation(); + switch(rotation) + { + case 0: // '\0' + rotation = 90; + break; + + case 1: // '\001' + rotation = 0; + break; + + case 2: // '\002' + rotation = 270; + break; + + case 3: // '\003' + rotation = 180; + break; + + default: + rotation = 90; + break; + } + camera.setDisplayOrientation(rotation); + android.hardware.Camera.Parameters params = camera.getParameters(); + tryStopPreview(); + tryStartPreview(); + + } + + public void toggleFlash(View view) { + camera.startPreview(); + android.hardware.Camera.Parameters camParams = camera.getParameters(); + //If the flash is set to off + try { + if (camParams.getFlashMode().equals(Parameters.FLASH_MODE_OFF) && !(camParams.getFlashMode().equals(Parameters.FLASH_MODE_TORCH)) && !(camParams.getFlashMode().equals(Parameters.FLASH_MODE_ON))) + camParams.setFlashMode(Parameters.FLASH_MODE_TORCH); + else //if(camParams.getFlashMode() == Parameters.FLASH_MODE_ON || camParams.getFlashMode()== Parameters.FLASH_MODE_TORCH) + camParams.setFlashMode(Parameters.FLASH_MODE_OFF); + } catch(RuntimeException e) { + } + + try { + // camera.setParameters(camParams); + camera.setPreviewDisplay(holder); + camera.setPreviewCallback(previewCb); + camera.startPreview(); + if (android.os.Build.VERSION.SDK_INT >= 14) { + camera.autoFocus(autoFocusCb); // We are not using any of the + // continuous autofocus modes as that does not seem to work + // well with flash setting of "on"... At least with this + // simple and stupid focus method, we get to turn the flash + // on during autofocus. + camParams.setFocusMode(Camera.Parameters.FOCUS_MODE_CONTINUOUS_PICTURE); + } + //tryStopPreview(); + //tryStartPreview(); + //camParams.setFocusMode(Camera.Parameters.FOCUS_MODE_CONTINUOUS_PICTURE); + camera.setParameters(camParams); + } catch(RuntimeException e) { + Log.d("csZBar", (new StringBuilder("Unsupported camera parameter reported for flash mode: ")).append(flashMode).toString()); + } catch (IOException e) { + Log.d("csZBar", (new StringBuilder("Wrong holder data")).append(flashMode).toString()); + } + } // Continuously auto-focus ----------------------------------------- // For API Level < 14 @@ -380,8 +497,43 @@ public Collection getFormats() { private void tryStartPreview () { if(holder != null) { try { + int rotation = getWindowManager().getDefaultDisplay().getRotation(); + switch(rotation) + { + case 0: // '\0' + rotation = 90; + break; + + case 1: // '\001' + rotation = 0; + break; + + case 2: // '\002' + rotation = 270; + break; + + case 3: // '\003' + rotation = 180; + break; + + default: + rotation = 90; + break; + } // 90 degrees rotation for Portrait orientation Activity. - camera.setDisplayOrientation(90); + // camera.setDisplayOrientation(rotation); + setCameraDisplayOrientation(this, 0); + + android.hardware.Camera.Parameters camParams = camera.getParameters(); + + //camParams.setFlashMode(Parameters.FLASH_MODE_TORCH); + + try { + camParams.setFocusMode(Camera.Parameters.FOCUS_MODE_CONTINUOUS_PICTURE); + camera.setParameters(camParams); + } catch (Exception e) { + // TODO: don't swallow + } camera.setPreviewDisplay(holder); camera.setPreviewCallback(previewCb); diff --git a/android/libs/arm64-v8a/libiconv.so b/android/libs/arm64-v8a/libiconv.so new file mode 100755 index 0000000..31c8e4f Binary files /dev/null and b/android/libs/arm64-v8a/libiconv.so differ diff --git a/android/libs/arm64-v8a/libzbarjni.so b/android/libs/arm64-v8a/libzbarjni.so new file mode 100755 index 0000000..9e0ce49 Binary files /dev/null and b/android/libs/arm64-v8a/libzbarjni.so differ diff --git a/android/libs/armeabi-v7a/libiconv.so b/android/libs/armeabi-v7a/libiconv.so old mode 100644 new mode 100755 index 2bcbb70..08c76d2 Binary files a/android/libs/armeabi-v7a/libiconv.so and b/android/libs/armeabi-v7a/libiconv.so differ diff --git a/android/libs/armeabi-v7a/libzbarjni.so b/android/libs/armeabi-v7a/libzbarjni.so old mode 100644 new mode 100755 index 2693dbb..ca099e6 Binary files a/android/libs/armeabi-v7a/libzbarjni.so and b/android/libs/armeabi-v7a/libzbarjni.so differ diff --git a/android/libs/armeabi/libiconv.so b/android/libs/armeabi/libiconv.so old mode 100644 new mode 100755 index 9c7150d..709c9e5 Binary files a/android/libs/armeabi/libiconv.so and b/android/libs/armeabi/libiconv.so differ diff --git a/android/libs/armeabi/libzbarjni.so b/android/libs/armeabi/libzbarjni.so old mode 100644 new mode 100755 index 3d4a8ac..362922d Binary files a/android/libs/armeabi/libzbarjni.so and b/android/libs/armeabi/libzbarjni.so differ diff --git a/android/libs/x86/libiconv.so b/android/libs/x86/libiconv.so old mode 100644 new mode 100755 index 6ab43e5..42c5abd Binary files a/android/libs/x86/libiconv.so and b/android/libs/x86/libiconv.so differ diff --git a/android/libs/x86/libzbarjni.so b/android/libs/x86/libzbarjni.so old mode 100644 new mode 100755 index d64f517..025395d Binary files a/android/libs/x86/libzbarjni.so and b/android/libs/x86/libzbarjni.so differ diff --git a/android/res/drawable/camera_flash.png b/android/res/drawable/camera_flash.png new file mode 100644 index 0000000..b6cf708 Binary files /dev/null and b/android/res/drawable/camera_flash.png differ diff --git a/android/res/layout/cszbarscanner.xml b/android/res/layout/cszbarscanner.xml index 4566d31..20bea7f 100644 --- a/android/res/layout/cszbarscanner.xml +++ b/android/res/layout/cszbarscanner.xml @@ -1,8 +1,8 @@ + android:textSize="15pt" /> + android:layout_width="wrap_content" + android:layout_height="fill_parent" + android:layout_gravity="center_horizontal|bottom"> + + diff --git a/ios/AlmaZBarReaderViewController.m b/ios/AlmaZBarReaderViewController.m index 9144939..0f8abf1 100644 --- a/ios/AlmaZBarReaderViewController.m +++ b/ios/AlmaZBarReaderViewController.m @@ -3,10 +3,9 @@ // BarCodeMix // // Created by eCompliance on 23/01/15. -// -// #import "AlmaZBarReaderViewController.h" +#import "CsZbar.h" @interface AlmaZBarReaderViewController () @@ -17,6 +16,29 @@ @implementation AlmaZBarReaderViewController - (void)viewDidLoad { [super viewDidLoad]; // Do any additional setup after loading the view. + UIButton *button = [UIButton buttonWithType:UIButtonTypeRoundedRect]; + //[button setTitle:@"Flash" forState:UIControlStateNormal]; + [button sizeToFit]; + CGRect screenRect = [[UIScreen mainScreen] bounds]; + //[button setContentEdgeInsets:UIEdgeInsetsMake(20, 30, 20, 30)]; + CGRect frame; + + if (screenRect.size.height > (screenRect.size.width)) { + frame = CGRectMake(0,0, screenRect.size.width*(0.15), screenRect.size.height*0.15); + }else{ + frame = CGRectMake(0,0, screenRect.size.width*(0.10), screenRect.size.height*0.20); + } + + button.frame =frame; + button.layer.cornerRadius = 10; + button.clipsToBounds = YES; + + [button addTarget:self action:@selector(buttonPressed:) forControlEvents:UIControlEventTouchUpInside]; + [self.view addSubview:button]; +} + +- (BOOL)prefersStatusBarHidden { + return YES; } - (void)didReceiveMemoryWarning { @@ -24,18 +46,34 @@ - (void)didReceiveMemoryWarning { // Dispose of any resources that can be recreated. } --(BOOL)shouldAutorotate{ - return NO; +//Techedge Changes NSS fase 2 +- (void)buttonPressed: (UIButton *) button { + CsZBar *obj = [[CsZBar alloc] init]; + + [obj toggleflash]; } -/* -#pragma mark - Navigation +- (BOOL)shouldAutorotate{ + return YES; +} + +- (void) didRotateFromInterfaceOrientation:(UIInterfaceOrientation) fromInterfaceOrientation { + // AlmaZBarReaderViewController.scanner.scanner.cameraOverlayView = poli + // NSDictionary *params = (NSDictionary*) [command argumentAtIndex:0]; + BOOL drawSight = true;//[params objectForKey:@"drawSight"] ? [[params objectForKey:@"drawSight"] boolValue] : true; + + if (drawSight) { + CGRect screenRect = [[UIScreen mainScreen] bounds]; + CGFloat screenWidth = screenRect.size.width; + CGFloat screenHeight = screenRect.size.height; + CGFloat dim = screenWidth < screenHeight ? screenWidth / 1.1 : screenHeight / 1.1; + UIView *polygonView = [[UIView alloc] initWithFrame: CGRectMake ( (screenWidth/2) - (dim/2), (screenHeight/2) - (dim/2), dim, dim)]; -// In a storyboard-based application, you will often want to do a little preparation before navigation -- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender { - // Get the new view controller using [segue destinationViewController]. - // Pass the selected object to the new view controller. + UIView *lineView = [[UIView alloc] initWithFrame:CGRectMake(0,dim / 2, dim, 1)]; + lineView.backgroundColor = [UIColor redColor]; + [polygonView addSubview:lineView]; + self.cameraOverlayView = polygonView; + } } -*/ @end diff --git a/ios/CsZBar.h b/ios/CsZBar.h index e774ae2..f043e6c 100644 --- a/ios/CsZBar.h +++ b/ios/CsZBar.h @@ -1,9 +1,14 @@ #import #import "ZBarSDK.h" +#import @interface CsZBar : CDVPlugin - (void)scan: (CDVInvokedUrlCommand*)command; +- (void)toggleflash; + + + @end diff --git a/ios/CsZBar.m b/ios/CsZBar.m index 6df2520..45a15ab 100644 --- a/ios/CsZBar.m +++ b/ios/CsZBar.m @@ -1,4 +1,5 @@ #import "CsZBar.h" +#import #import "AlmaZBarReaderViewController.h" #pragma mark - State @@ -7,8 +8,8 @@ @interface CsZBar () @property bool scanInProgress; @property NSString *scanCallbackId; @property AlmaZBarReaderViewController *scanReader; -@end +@end #pragma mark - Synthesize @@ -18,20 +19,25 @@ @implementation CsZBar @synthesize scanCallbackId; @synthesize scanReader; - #pragma mark - Cordova Plugin -- (void)pluginInitialize -{ +- (void)pluginInitialize { self.scanInProgress = NO; } +- (void)willRotateToInterfaceOrientation:(UIInterfaceOrientation)toInterfaceOrientation duration:(NSTimeInterval)duration { + return; +} + +- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation { + return YES; +} #pragma mark - Plugin API -- (void)scan: (CDVInvokedUrlCommand*)command; +- (void)scan: (CDVInvokedUrlCommand*)command; { - if(self.scanInProgress) { + if (self.scanInProgress) { [self.commandDelegate sendPluginResult: [CDVPluginResult resultWithStatus: CDVCommandStatus_ERROR @@ -53,81 +59,123 @@ - (void)scan: (CDVInvokedUrlCommand*)command; // as not all devices will have a rear-facing camera. self.scanReader.cameraDevice = UIImagePickerControllerCameraDeviceFront; } + self.scanReader.cameraFlashMode = UIImagePickerControllerCameraFlashModeOn; + NSString *flash = [params objectForKey:@"flash"]; - if([flash isEqualToString:@"on"]) { + + if ([flash isEqualToString:@"on"]) { self.scanReader.cameraFlashMode = UIImagePickerControllerCameraFlashModeOn; - } else if([flash isEqualToString:@"off"]) { + } else if ([flash isEqualToString:@"off"]) { self.scanReader.cameraFlashMode = UIImagePickerControllerCameraFlashModeOff; + }else if ([flash isEqualToString:@"auto"]) { + self.scanReader.cameraFlashMode = UIImagePickerControllerCameraFlashModeAuto; } // Hack to hide the bottom bar's Info button... originally based on http://stackoverflow.com/a/16353530 - UIView *infoButton = [[[[[self.scanReader.view.subviews objectAtIndex:2] subviews] objectAtIndex:0] subviews] objectAtIndex:3]; + NSInteger infoButtonIndex; + if ([[[UIDevice currentDevice] systemVersion] compare:@"10.0" options:NSNumericSearch] != NSOrderedAscending) { + infoButtonIndex = 1; + } else { + infoButtonIndex = 3; + } + UIView *infoButton = [[[[[self.scanReader.view.subviews objectAtIndex:2] subviews] objectAtIndex:0] subviews] objectAtIndex:infoButtonIndex]; [infoButton setHidden:YES]; + //UIButton *button = [UIButton buttonWithType:UIButtonTypeSystem]; [button setTitle:@"Press Me" forState:UIControlStateNormal]; [button sizeToFit]; [self.view addSubview:button]; + CGRect screenRect = [[UIScreen mainScreen] bounds]; + CGFloat screenWidth = screenRect.size.width; + CGFloat screenHeight = screenRect.size.height; + BOOL drawSight = [params objectForKey:@"drawSight"] ? [[params objectForKey:@"drawSight"] boolValue] : true; - if(drawSight){ - CGRect screenRect = [[UIScreen mainScreen] bounds]; - CGFloat screenWidth = screenRect.size.width; - CGFloat screenHeight = screenRect.size.height; + UIToolbar *toolbarViewFlash = [[UIToolbar alloc] init]; + + //The bar length it depends on the orientation + toolbarViewFlash.frame = CGRectMake(0.0, 0, (screenWidth > screenHeight ?screenWidth:screenHeight), 44.0); + toolbarViewFlash.barStyle = UIBarStyleBlackOpaque; + UIBarButtonItem *buttonFlash = [[UIBarButtonItem alloc] initWithTitle:@"Flash" style:UIBarButtonItemStyleDone target:self action:@selector(toggleflash)]; + + NSArray *buttons = [NSArray arrayWithObjects: buttonFlash, nil]; + [toolbarViewFlash setItems:buttons animated:NO]; + [self.scanReader.view addSubview:toolbarViewFlash]; + + if (drawSight) { CGFloat dim = screenWidth < screenHeight ? screenWidth / 1.1 : screenHeight / 1.1; - UIView *polygonView = [[UIView alloc] initWithFrame: CGRectMake ( (screenWidth/2) - (dim/2), (screenHeight/2) - (dim/2), dim, dim)]; - //polygonView.center = self.scanReader.view.center; - //polygonView.layer.borderColor = [UIColor greenColor].CGColor; - //polygonView.layer.borderWidth = 3.0f; - - UIView *lineView = [[UIView alloc] initWithFrame:CGRectMake(dim / 2, 0, 1, dim)]; + UIView *polygonView = [[UIView alloc] initWithFrame: CGRectMake ( (screenWidth/2) - (dim/2), (screenHeight/2) - (dim/2), dim, dim)]; + + UIView *lineView = [[UIView alloc] initWithFrame:CGRectMake(0,dim / 2, dim, 1)]; lineView.backgroundColor = [UIColor redColor]; [polygonView addSubview:lineView]; self.scanReader.cameraOverlayView = polygonView; - //[self.scanReader.view addSubview:polygonView]; } - [self.viewController presentModalViewController: self.scanReader animated: YES]; + [self.viewController presentViewController:self.scanReader animated:YES completion:nil]; } } +- (void)toggleflash { + AVCaptureDevice *device = [AVCaptureDevice defaultDeviceWithMediaType:AVMediaTypeVideo]; + + [device lockForConfiguration:nil]; + if (device.torchAvailable == 1) { + if (device.torchMode == 0) { + [device setTorchMode:AVCaptureTorchModeOn]; + [device setFlashMode:AVCaptureFlashModeOn]; + } else { + [device setTorchMode:AVCaptureTorchModeOff]; + [device setFlashMode:AVCaptureFlashModeOff]; + } + } + + [device unlockForConfiguration]; +} #pragma mark - Helpers -- (void)sendScanResult: (CDVPluginResult*)result -{ +- (void)sendScanResult: (CDVPluginResult*)result { [self.commandDelegate sendPluginResult: result callbackId: self.scanCallbackId]; } - #pragma mark - ZBarReaderDelegate -- (void)imagePickerController:(UIImagePickerController*)picker didFinishPickingMediaWithInfo:(NSDictionary*)info -{ +- (void) imagePickerController:(UIImagePickerController *)picker didFinishPickingImage:(UIImage *)image editingInfo:(NSDictionary *)editingInfo { + return; +} + +- (void)imagePickerController:(UIImagePickerController*)picker didFinishPickingMediaWithInfo:(NSDictionary*)info { + if ([self.scanReader isBeingDismissed]) { + return; + } + id results = [info objectForKey: ZBarReaderControllerResults]; + ZBarSymbol *symbol = nil; - for(symbol in results) break; // get the first result - - [self.scanReader dismissModalViewControllerAnimated: YES]; - self.scanInProgress = NO; - [self sendScanResult: [CDVPluginResult - resultWithStatus: CDVCommandStatus_OK - messageAsString: symbol.data]]; + for (symbol in results) break; // get the first result + + [self.scanReader dismissViewControllerAnimated: YES completion: ^(void) { + self.scanInProgress = NO; + [self sendScanResult: [CDVPluginResult + resultWithStatus: CDVCommandStatus_OK + messageAsString: symbol.data]]; + }]; } -- (void) imagePickerControllerDidCancel:(UIImagePickerController*)picker -{ - [self.scanReader dismissModalViewControllerAnimated: YES]; - self.scanInProgress = NO; - [self sendScanResult: [CDVPluginResult - resultWithStatus: CDVCommandStatus_ERROR - messageAsString: @"cancelled"]]; +- (void) imagePickerControllerDidCancel:(UIImagePickerController*)picker { + [self.scanReader dismissViewControllerAnimated: YES completion: ^(void) { + self.scanInProgress = NO; + [self sendScanResult: [CDVPluginResult + resultWithStatus: CDVCommandStatus_ERROR + messageAsString: @"cancelled"]]; + }]; } -- (void) readerControllerDidFailToRead:(ZBarReaderController*)reader withRetry:(BOOL)retry -{ - [self.scanReader dismissModalViewControllerAnimated: YES]; - self.scanInProgress = NO; - [self sendScanResult: [CDVPluginResult - resultWithStatus: CDVCommandStatus_ERROR - messageAsString: @"Failed"]]; +- (void) readerControllerDidFailToRead:(ZBarReaderController*)reader withRetry:(BOOL)retry { + [self.scanReader dismissViewControllerAnimated: YES completion: ^(void) { + self.scanInProgress = NO; + [self sendScanResult: [CDVPluginResult + resultWithStatus: CDVCommandStatus_ERROR + messageAsString: @"Failed"]]; + }]; } - @end diff --git a/package.json b/package.json new file mode 100644 index 0000000..3a59007 --- /dev/null +++ b/package.json @@ -0,0 +1,43 @@ +{ + "name": "cordova-plugin-cszbar", + "version": "1.3.3", + "description": "Plugin to integrate with the ZBar barcode scanning library.", + "cordova": { + "id": "cordova-plugin-cszbar", + "platforms": [ + "android", + "ios" + ] + }, + "repository": { + "type": "git", + "url": "git+https://github.com/tjwoon/csZBar.git" + }, + "keywords": [ + "cszbar", + "zbar", + "barcode", + "qr", + "qr code", + "scanner", + "ecosystem:cordova", + "cordova-android", + "cordova-ios" + ], + "engines": [ + { + "name": "cordova-android", + "version": ">=3.0.0" + }, + { + "name": "cordova-ios", + "version": ">=3.0.0" + } + ], + "author": "TJ Woon ", + "license": "Apache 2.0", + "bugs": { + "url": "https://github.com/tjwoon/csZBar/issues" + }, + "homepage": "https://github.com/tjwoon/csZBar#readme" +} diff --git a/plugin.xml b/plugin.xml index 8d27f0c..dd43518 100644 --- a/plugin.xml +++ b/plugin.xml @@ -1,6 +1,7 @@ + xmlns:android="http://schemas.android.com/apk/res/android" + id="cordova-plugin-cszbar" version="1.3.2"> @@ -23,11 +24,10 @@ - - + android:screenOrientation="fullUser" + android:theme="@android:style/Theme.Black.NoTitleBar.Fullscreen" /> @@ -43,6 +43,7 @@ #88000000 #000000 + @@ -52,8 +53,16 @@ + + s + + + + + + @@ -62,12 +71,18 @@ + + + + For Barcode Scanning + + - +