@sapui5/sap.ndc 1.96.24 → 1.96.25

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@sapui5/sap.ndc",
3
- "version": "1.96.24",
3
+ "version": "1.96.25",
4
4
  "description": "SAPUI5 Library sap.ndc",
5
5
  "homepage": "https://sap.github.io/ui5-tooling/pages/SAPUI5/",
6
6
  "author": "SAP SE (https://www.sap.com)",
@@ -5,7 +5,7 @@
5
5
  <vendor>SAP SE</vendor>
6
6
  <copyright>SAPUI5
7
7
  * (c) Copyright 2009-2022 SAP SE. All rights reserved.</copyright>
8
- <version>1.96.24</version>
8
+ <version>1.96.25</version>
9
9
 
10
10
  <documentation>SAPUI5 library with controls with native device capabilities.</documentation>
11
11
 
@@ -82,9 +82,10 @@ sap.ui.define([
82
82
  /* =========================================================== */
83
83
  oStream,
84
84
  oScanDialog,
85
+ oBarcodeScannerUIContainer,
86
+ oVideoTrack,
85
87
  oBarcodeVideoDOM,
86
88
  oBarcodeCanvasDOM,
87
- oContext,
88
89
  oBarcodeOverlayDOM,
89
90
  oBarcodeHighlightDOM,
90
91
 
@@ -107,14 +108,11 @@ sap.ui.define([
107
108
  },
108
109
  deviceId: undefined,
109
110
  preferFrontCamera: false,
110
- zoom: null,
111
111
  enableGS1Header: false
112
112
  },
113
113
  scanDialog: {
114
114
  title: "", //oDialogTitle
115
115
  onLiveUpdate: null, //Live update function
116
- imgTruncX: 0,
117
- imgTruncY: 0,
118
116
  barcodeOverlaySetup: false,
119
117
  isNoScanner: false,
120
118
  scanningStartTime: 0,
@@ -376,7 +374,7 @@ sap.ui.define([
376
374
  * @private
377
375
  */
378
376
  function loadZXingCPPAPI() {
379
- Log.info("BarcodeScanner.loadZXingCPPAPI: load ZXingCPP API");
377
+ Log.debug("BarcodeScanner.loadZXingCPPAPI: load ZXingCPP API");
380
378
  updateScannerAPI("ZXingCPP", oScannerAPIStatus.Loading);
381
379
  sap.ui.require([
382
380
  "sap/ndc/thirdparty/zxingcpp/zxing_reader"
@@ -515,7 +513,7 @@ sap.ui.define([
515
513
  .catch(
516
514
  function(oErr) {
517
515
  oModel.setProperty("/devices/needCheck", false);
518
- Log.error("BarcodeScanner.getDeviceCameras: Can not get device cameras.\n" + oErr);
516
+ Log.error("BarcodeScanner.getDeviceCameras: Can not get device cameras.\nError Message: " + oErr);
519
517
  });
520
518
  }
521
519
 
@@ -534,11 +532,13 @@ sap.ui.define([
534
532
  Log.debug("BarcodeScanner.findMainCamera: can not find the main camera.");
535
533
  fnCallback();
536
534
  } else {
537
- var oCamera = aCamerasClone.pop();
535
+ var oCamera = aCamerasClone[aCamerasClone.length - 1];
538
536
  var oConstraints = deepClone(oModel.getProperty("/config/defaultConstraints"));
539
537
  oConstraints.video.deviceId = {
540
538
  exact: oCamera.deviceId
541
539
  };
540
+ var oVideoResolution = calculateVideoResolution();
541
+ oConstraints.video = Object.assign(oConstraints.video, oVideoResolution);
542
542
  window.navigator.mediaDevices
543
543
  .getUserMedia(oConstraints)
544
544
  .then(
@@ -553,7 +553,7 @@ sap.ui.define([
553
553
  Log.debug("BarcodeScanner.findMainCamera: the main camera is " + oCamera.deviceId);
554
554
  oStream = stream;
555
555
  if (oStream) {
556
- openBarcodeScannerDialogContains();
556
+ playbackVideoAndDecode();
557
557
  } else {
558
558
  oScanDialog.getModel().setProperty("/isNoScanner", true);
559
559
  openBarcodeInputDialog();
@@ -561,11 +561,19 @@ sap.ui.define([
561
561
  }, function() {
562
562
  videoTrack.stop();
563
563
  Log.debug("BarcodeScanner.findMainCamera: " + oCamera.deviceId + " is not the main camera, check the next camera");
564
+ aCamerasClone.pop();
564
565
  fnCheckStream();
565
566
  });
566
567
  }
567
568
  ).catch(
568
- function() {
569
+ function (error) {
570
+ Log.debug("BarcodeScanner.findMainCamera: getUserMedia() failed.\nError Message: " + error);
571
+ if (oModel.getProperty("/config/defaultConstraints/video/zoom") !== undefined) {
572
+ Log.debug("BarcodeScanner.findMainCamera: getUserMedia() failed maybe caused by unsupported constraint 'zoom', delete it and try again.");
573
+ delete oModel.getProperty("/config/defaultConstraints/video").zoom;
574
+ } else {
575
+ aCamerasClone.pop();
576
+ }
569
577
  fnCheckStream();
570
578
  }
571
579
  );
@@ -613,7 +621,7 @@ sap.ui.define([
613
621
  reject();
614
622
  }
615
623
  }).catch(function(oError) {
616
- Log.debug("BarcodeScanner.checkFlashLight: Camera not started or not available\n" + oError);
624
+ Log.debug("BarcodeScanner.checkFlashLight: Camera not started or not available.\nError Message: " + oError);
617
625
  reject();
618
626
  });
619
627
  });
@@ -804,21 +812,29 @@ sap.ui.define([
804
812
  );
805
813
 
806
814
  oScanDialog.setBusy(false);
807
- oScanDialog.open();
808
815
  }
809
816
 
810
817
  /**
811
- * Initializes ZXing/ZXingCPP code reader scan, video device gets turned on and starts waiting for barcode
818
+ * Open correct camera
812
819
  * @private
813
820
  */
814
- function openBarcodeScannerDialog() {
821
+ function openCorrectCamera() {
815
822
  if (!oModel.getProperty("/config/preferFrontCamera")) {
816
823
  delete oModel.getProperty("/config/defaultConstraints/video").facingMode;
817
824
  var oDevices = oModel.getProperty("/devices");
818
- if (!oModel.getProperty("/config/deviceId") && !oDevices.mainCamera && !Device.os.ios && oDevices.needCheck && oDevices.all.length > 1) {
825
+ // when:
826
+ // a. no camera seleted
827
+ // b. main camera not found (no camera label contains '0, facing back')
828
+ // c. not iphone devices
829
+ // d. not Mac, or not ipad devices with Safari browser
830
+ // e. needCheck flag !== false
831
+ // f. camera list length > 1
832
+ // need to find main camera
833
+ if (!oModel.getProperty("/config/deviceId") && !oDevices.mainCamera && !Device.os.ios && !Device.os.macintosh && oDevices.needCheck && oDevices.all.length > 1) {
834
+ // if back camera list length > 1, find main camera in back camera list, or find it in all camera list
819
835
  var oCameras = oDevices.back.length > 1 ? oDevices.back : oDevices.all;
820
836
  var sCategory = oDevices.back.length > 1 ? "back" : "all";
821
- Log.debug("BarcodeScanner.openBarcodeScannerDialog: start to find the main camera in " + sCategory + " camera list.");
837
+ Log.debug("BarcodeScanner.openCorrectCamera: start to find the main camera in " + sCategory + " camera list.");
822
838
  findMainCamera(oCameras, openCamera);
823
839
  return;
824
840
  }
@@ -826,7 +842,8 @@ sap.ui.define([
826
842
  openCamera();
827
843
  }
828
844
 
829
- function openCamera() {
845
+ function openCamera(bAttachOrientationChangeListener) {
846
+ Log.debug("BarcodeScanner.openCamera: start to open camera");
830
847
  if (oModel.getProperty("/config/deviceId")) {
831
848
  // if config/deviceId is set, use it as camera deviceId directly
832
849
  delete oModel.getProperty("/config/defaultConstraints/video").facingMode;
@@ -846,13 +863,16 @@ sap.ui.define([
846
863
  oModel.setProperty("/config/defaultConstraints/video/facingMode", "environment");
847
864
  }
848
865
  }
866
+ var oConstraints = deepClone(oModel.getProperty("/config/defaultConstraints"));
867
+ var oVideoResolution = calculateVideoResolution();
868
+ oConstraints.video = Object.assign(oConstraints.video, oVideoResolution);
849
869
  window.navigator.mediaDevices
850
- .getUserMedia(oModel.getProperty("/config/defaultConstraints"))
870
+ .getUserMedia(oConstraints)
851
871
  .then(
852
872
  function(stream) {
853
873
  oStream = stream;
854
874
  if (oStream) {
855
- openBarcodeScannerDialogContains();
875
+ playbackVideoAndDecode(bAttachOrientationChangeListener);
856
876
  } else {
857
877
  oModel.setProperty("/scanDialog/isNoScanner", true);
858
878
  openBarcodeInputDialog();
@@ -860,14 +880,21 @@ sap.ui.define([
860
880
  }
861
881
  )
862
882
  .catch(
863
- function() {
864
- oModel.setProperty("/scanDialog/isNoScanner", true);
865
- openBarcodeInputDialog();
883
+ function (error) {
884
+ Log.debug("BarcodeScanner.openCamera: getUserMedia() failed.\nError Message: " + error);
885
+ if (oModel.getProperty("/config/defaultConstraints/video/zoom") !== undefined) {
886
+ Log.debug("BarcodeScanner.openCamera: getUserMedia() failed maybe caused by unsupported constraint 'zoom', delete it and try again.");
887
+ delete oModel.getProperty("/config/defaultConstraints/video").zoom;
888
+ openCamera();
889
+ } else {
890
+ oModel.setProperty("/scanDialog/isNoScanner", true);
891
+ openBarcodeInputDialog();
892
+ }
866
893
  }
867
894
  );
868
895
  }
869
896
 
870
- function getScanDialog() {
897
+ function openScanDialog() {
871
898
  oModel.checkUpdate(true);
872
899
  var oDialogModel;
873
900
 
@@ -910,8 +937,25 @@ sap.ui.define([
910
937
  oScanDialog.setModel(oResourceModel, "i18n");
911
938
  }
912
939
 
940
+ oScanDialog.addStyleClass('sapUiNoContentPadding');
941
+ oScanDialog.setBusy(true);
942
+
913
943
  if (isScannerAPIAvailable("ZXingCPP") && isUserMediaAccessSupported()) {
914
- openBarcodeScannerDialog();
944
+ oScanDialog.attachAfterOpen(function() {
945
+ openCorrectCamera();
946
+ });
947
+ oScanDialog.destroyContent();
948
+ oBarcodeHighlightDOM = undefined;
949
+ oBarcodeOverlayDOM = undefined;
950
+ oBarcodeVideoDOM = undefined;
951
+ oBarcodeCanvasDOM = undefined;
952
+
953
+ oBarcodeScannerUIContainer = new BarcodeScannerUIContainer();
954
+ oScanDialog.addContent(oBarcodeScannerUIContainer);
955
+ oScanDialog.setContentWidth('100%');
956
+ oScanDialog.setContentHeight('100%');
957
+
958
+ oModel.setProperty("/scanDialog/barcodeOverlaySetup", false);
915
959
  } else {
916
960
  if (oModel.getProperty("/available")) {
917
961
  oModel.setProperty("/scanDialog/isNoScanner", false);
@@ -920,8 +964,7 @@ sap.ui.define([
920
964
  }
921
965
  openBarcodeInputDialog();
922
966
  }
923
-
924
- return oScanDialog;
967
+ oScanDialog.open();
925
968
  }
926
969
 
927
970
  /**
@@ -941,39 +984,39 @@ sap.ui.define([
941
984
  */
942
985
  function scanWithCordova() {
943
986
  var options;
944
- if (oModel.getProperty("/config/preferFrontCamera")) {
945
- options = {
946
- preferFrontCamera: true
947
- };
948
- }
949
- oModel.getProperty("/apis/Cordova/scannerAPI").scan(
950
- function (oResult) {
951
- if (oResult.cancelled === "false" || !oResult.cancelled) {
952
- oResult.cancelled = false;
953
- var onFnSuccess = oModel.getProperty("/callBackHandler/onFnSuccess");
954
- if (typeof onFnSuccess === "function") {
955
- onFnSuccess(oResult);
956
- }
957
- } else {
958
- getScanDialog();
987
+ if (oModel.getProperty("/config/preferFrontCamera")) {
988
+ options = {
989
+ preferFrontCamera: true
990
+ };
991
+ }
992
+ oModel.getProperty("/apis/Cordova/scannerAPI").scan(
993
+ function (oResult) {
994
+ if (oResult.cancelled === "false" || !oResult.cancelled) {
995
+ oResult.cancelled = false;
996
+ var onFnSuccess = oModel.getProperty("/callBackHandler/onFnSuccess");
997
+ if (typeof onFnSuccess === "function") {
998
+ onFnSuccess(oResult);
959
999
  }
960
- oModel.setProperty("/bReady", true);
961
- },
962
- function (oEvent) {
963
- Log.error("BarcodeScanner.scanWithCordova: Barcode scanning failed.");
964
- oModel.setProperty("/bReady", true);
965
- var onFnFail = oModel.getProperty("/callBackHandler/onFnFail");
966
- if (typeof onFnFail === "function") {
967
- if (typeof oEvent === "string") {
968
- var str = oEvent;
969
- oEvent = {"text": str};
970
- Log.debug("BarcodeScanner.scanWithCordova: Change the type of oEvent from string to object");
971
- }
972
- onFnFail(oEvent);
1000
+ } else {
1001
+ openScanDialog();
1002
+ }
1003
+ oModel.setProperty("/bReady", true);
1004
+ },
1005
+ function (oEvent) {
1006
+ Log.error("BarcodeScanner.scanWithCordova: Barcode scanning failed.");
1007
+ oModel.setProperty("/bReady", true);
1008
+ var onFnFail = oModel.getProperty("/callBackHandler/onFnFail");
1009
+ if (typeof onFnFail === "function") {
1010
+ if (typeof oEvent === "string") {
1011
+ var str = oEvent;
1012
+ oEvent = {"text": str};
1013
+ Log.debug("BarcodeScanner.scanWithCordova: Change the type of oEvent from string to object");
973
1014
  }
974
- },
975
- options
976
- );
1015
+ onFnFail(oEvent);
1016
+ }
1017
+ },
1018
+ options
1019
+ );
977
1020
  }
978
1021
 
979
1022
  /**
@@ -984,7 +1027,7 @@ sap.ui.define([
984
1027
  if (checkScannerAPIStatus("ZXingCPP", oScannerAPIStatus.Initial)) {
985
1028
  Log.debug("BarcodeScanner.scanWithZXingCPP: ZXingCPP instances is not loaded, start to load them.");
986
1029
  loadZXingCPPInstance(function() {
987
- getScanDialog();
1030
+ openScanDialog();
988
1031
  }, function() {
989
1032
  if (isScannerAPIAvailable("ZebraEnterpriseBrowser")) {
990
1033
  setCurrentScannerAPI("ZebraEnterpriseBrowser");
@@ -993,71 +1036,47 @@ sap.ui.define([
993
1036
  setCurrentScannerAPI("unknown");
994
1037
  Log.warning("BarcodeScanner.scanWithZXingCPP: Zebra is unavailable too, set the current scanner API to unknown.");
995
1038
  }
996
- getScanDialog();
1039
+ openScanDialog();
997
1040
  });
998
1041
  } else {
999
- getScanDialog();
1042
+ Log.debug("BarcodeScanner.scanWithZXingCPP: get scan dialog.");
1043
+ openScanDialog();
1000
1044
  }
1001
1045
  }
1002
1046
 
1003
1047
  /**
1004
- * Opens Barcode Scanner dialog, called when code reader is ready
1048
+ * Playback the video, then decode via ZXingCPP
1005
1049
  * @private
1006
1050
  */
1007
- function openBarcodeScannerDialogContains() {
1008
- var oBarcodeScannerUIContainer;
1009
- Log.debug("BarcodeScanner.openBarcodeScannerDialogContains: Use ZXingCPP to read the barcode.");
1010
- oScanDialog.attachAfterOpen(function() {
1011
- // Dev note: if video element dom reference is unavailable at this point (console exception)
1012
- // some error happened during dialog creation and may not be directly related to video element
1013
- oScanDialog.getEndButton().setEnabled(true);
1014
- oScanDialog.setBusy(false);
1015
-
1016
- if (!oBarcodeHighlightDOM) {
1017
- oBarcodeHighlightDOM = oBarcodeScannerUIContainer.getDomRef('highlight');
1018
- }
1019
- if (!oBarcodeVideoDOM) {
1020
- oBarcodeVideoDOM = oBarcodeScannerUIContainer ? document.createElement("video") : undefined;
1021
- if (oBarcodeVideoDOM) {
1022
- oBarcodeVideoDOM.setAttribute("id", "video");
1023
- oBarcodeVideoDOM.setAttribute("autoplay", "autoplay");
1024
- oBarcodeVideoDOM.setAttribute("webkit-playsinline", "webkit-playsinline");
1025
- oBarcodeVideoDOM.setAttribute("playsinline", "playsinline");
1026
- }
1027
- }
1028
- if (!oBarcodeCanvasDOM) {
1029
- oBarcodeCanvasDOM = oBarcodeScannerUIContainer ? oBarcodeScannerUIContainer.getDomRef('canvas') : undefined;
1030
- oContext = oBarcodeCanvasDOM.getContext("2d", { willReadFrequently: true });
1031
- }
1032
- try {
1033
- oBarcodeVideoDOM.srcObject = oStream;
1034
- oBarcodeVideoDOM.play().then(function() {
1035
- oBarcodeCanvasDOM.width = oBarcodeVideoDOM.videoWidth;
1036
- oBarcodeCanvasDOM.height = oBarcodeVideoDOM.videoHeight;
1037
- decodeWithZXingCPP();
1038
- });
1039
- } catch (err) {
1040
- Log.debug("BarcodeScanner.openBarcodeScannerDialogContains is failed. error: " + err);
1041
- }
1042
- });
1043
- oScanDialog.destroyContent();
1044
- oBarcodeHighlightDOM = undefined;
1045
- oBarcodeOverlayDOM = undefined;
1046
- oBarcodeVideoDOM = undefined;
1047
-
1048
- oBarcodeCanvasDOM = undefined;
1049
- oContext = undefined;
1050
-
1051
- oBarcodeScannerUIContainer = new BarcodeScannerUIContainer();
1052
- oScanDialog.addContent(oBarcodeScannerUIContainer);
1053
-
1054
- oScanDialog.setContentWidth('100%');
1055
- oScanDialog.setContentHeight('100%');
1056
- oScanDialog.addStyleClass('sapUiNoContentPadding');
1057
- oScanDialog.setBusy(true);
1058
- oScanDialog.open();
1051
+ function playbackVideoAndDecode(bAttachOrientationChangeListener) {
1052
+ // Dev note: if video element dom reference is unavailable at this point (console exception)
1053
+ // some error happened during dialog creation and may not be directly related to video element
1054
+ oScanDialog.getEndButton().setEnabled(true);
1055
+ oScanDialog.setBusy(false);
1059
1056
 
1060
- oModel.setProperty("/scanDialog/barcodeOverlaySetup", false);
1057
+ if (!oBarcodeHighlightDOM) {
1058
+ oBarcodeHighlightDOM = oBarcodeScannerUIContainer.getDomRef('highlight');
1059
+ }
1060
+ if (!oBarcodeVideoDOM) {
1061
+ oBarcodeVideoDOM = oBarcodeScannerUIContainer ? oBarcodeScannerUIContainer.getDomRef('video') : undefined;
1062
+ }
1063
+ try {
1064
+ oBarcodeVideoDOM.srcObject = oStream;
1065
+ oBarcodeVideoDOM.play().then(function() {
1066
+ // show scan overlay box
1067
+ scanFrame();
1068
+ if (Device.support.orientation && bAttachOrientationChangeListener !== false) {
1069
+ Device.orientation.attachHandler(orientationChangeListener);
1070
+ }
1071
+ Log.debug("BarcodeScanner.playbackVideoAndDecode: video screen size " + oBarcodeVideoDOM.videoHeight + "X" + oBarcodeVideoDOM.videoWidth);
1072
+ oVideoTrack = typeof oStream.stop === "function" ? oStream : oStream.getTracks()[0];
1073
+ var settings = oVideoTrack.getSettings();
1074
+ Log.debug("BarcodeScanner.playbackVideoAndDecode: video screen frameRate is " + settings.frameRate + ", zoom is " + settings.zoom);
1075
+ decodeWithZXingCPP();
1076
+ });
1077
+ } catch (err) {
1078
+ Log.debug("BarcodeScanner.playbackVideoAndDecode is failed. error: " + err);
1079
+ }
1061
1080
  }
1062
1081
 
1063
1082
  /**
@@ -1065,31 +1084,43 @@ sap.ui.define([
1065
1084
  * @private
1066
1085
  */
1067
1086
  function decodeWithZXingCPP() {
1068
- Log.info("BarcodeScanner.decodeWithZXingCPP: start to decode");
1087
+ Log.debug("BarcodeScanner.decodeWithZXingCPP: start to decode");
1069
1088
  if (!oBarcodeVideoDOM || !oBarcodeVideoDOM.srcObject) {
1089
+ Log.debug("BarcodeScanner.decodeWithZXingCPP: video dom doesn't exist, stop decoding");
1070
1090
  return;
1071
1091
  }
1072
- scanFrame();
1073
1092
 
1074
1093
  try {
1075
- oContext.drawImage(oBarcodeVideoDOM, 0, 0, oBarcodeCanvasDOM.width, oBarcodeCanvasDOM.height);
1076
-
1077
- var imgWidth = oBarcodeCanvasDOM.width;
1078
- var imgHeight = oBarcodeCanvasDOM.height;
1079
- var imageData = oBarcodeCanvasDOM.getContext('2d').getImageData(0, 0, imgWidth, imgHeight);
1094
+ // use canvas to get video frame as image data
1095
+ if (!oBarcodeCanvasDOM) {
1096
+ oBarcodeCanvasDOM = oBarcodeScannerUIContainer ? document.createElement("canvas") : undefined;
1097
+ }
1098
+ if (!oBarcodeCanvasDOM) {
1099
+ Log.debug("BarcodeScanner.decodeWithZXingCPP: canvas dom doesn't exist, stop decoding");
1100
+ return;
1101
+ }
1102
+ var oContext = oBarcodeCanvasDOM.getContext("2d", { willReadFrequently: true });
1103
+ var imgWidth = oBarcodeVideoDOM.videoWidth;
1104
+ var imgHeight = oBarcodeVideoDOM.videoHeight;
1105
+ oBarcodeCanvasDOM.width = imgWidth;
1106
+ oBarcodeCanvasDOM.height = imgHeight;
1107
+ oContext.drawImage(oBarcodeVideoDOM, 0, 0, imgWidth, imgHeight);
1108
+ var imageData = oContext.getImageData(0, 0, imgWidth, imgHeight);
1080
1109
  var oData = imageData.data;
1110
+ // decode image data via ZXingCPP
1081
1111
  var buffer;
1082
1112
  var oZXingCPPScannerAPI = oModel.getProperty("/apis/ZXingCPP/scannerAPI");
1083
1113
  try {
1084
1114
  buffer = oZXingCPPScannerAPI._malloc(oData.length);
1085
1115
  oZXingCPPScannerAPI.HEAPU8.set(oData, buffer);
1086
1116
  } catch (err) {
1087
- Log.info("BarcodeScanner.decodeWithZXingCPP: zxing.HEAPU8 error: " + err);
1117
+ Log.error("BarcodeScanner.decodeWithZXingCPP: zxing.HEAPU8 error: " + err);
1088
1118
  }
1089
1119
  var results = oZXingCPPScannerAPI.readBarcodesFromPixmap(buffer, imgWidth, imgHeight, true, "", 1);
1090
1120
  oZXingCPPScannerAPI._free(buffer);
1091
1121
  var iSize = results.size();
1092
1122
  if (iSize > 0 && results.get(0).format) {
1123
+ Log.debug("BarcodeScanner.decodeWithZXingCPP: decode successful");
1093
1124
  var result = results.get(0);
1094
1125
  highlightResult(result);
1095
1126
  if (result.cancelled === "false" || !result.cancelled) {
@@ -1139,8 +1170,8 @@ sap.ui.define([
1139
1170
  }
1140
1171
 
1141
1172
  if (oBarcodeHighlightDOM) {
1142
- scaleX = oBarcodeCanvasDOM.clientWidth / oBarcodeVideoDOM.videoWidth;
1143
- scaleY = oBarcodeCanvasDOM.clientHeight / oBarcodeVideoDOM.videoHeight;
1173
+ scaleX = oBarcodeVideoDOM.clientWidth / oBarcodeVideoDOM.videoWidth;
1174
+ scaleY = oBarcodeVideoDOM.clientHeight / oBarcodeVideoDOM.videoHeight;
1144
1175
  if (result.position) {
1145
1176
  result.resultPoints = [
1146
1177
  result.position.topLeft,
@@ -1173,8 +1204,8 @@ sap.ui.define([
1173
1204
  oBarcodeHighlightDOM.hidden = false;
1174
1205
  oBarcodeHighlightDOM.style.top = top * scaleY + 'px';
1175
1206
  oBarcodeHighlightDOM.style.left = left * scaleX + 'px';
1176
- oBarcodeHighlightDOM.style.width = (right - left > 0 ? (right - left + oModel.getProperty("/scanDialog/imgTruncX")) * scaleX : 5) + 'px';
1177
- oBarcodeHighlightDOM.style.height = (bottom - top > 0 ? (bottom - top + oModel.getProperty("/scanDialog/imgTruncY")) * scaleY : 5) + 'px';
1207
+ oBarcodeHighlightDOM.style.width = (right - left > 0 ? (right - left) * scaleX : 5) + 'px';
1208
+ oBarcodeHighlightDOM.style.height = (bottom - top > 0 ? (bottom - top) * scaleY : 5) + 'px';
1178
1209
  }
1179
1210
  }
1180
1211
 
@@ -1190,22 +1221,81 @@ sap.ui.define([
1190
1221
  oBarcodeHighlightDOM.style.height = '0';
1191
1222
  }
1192
1223
 
1224
+ /**
1225
+ * If orientaition changed, reopen camera to maxsize video screen
1226
+ * @private
1227
+ */
1228
+ function orientationChangeListener(oNewOrientation) {
1229
+ oScanDialog.setBusy(true);
1230
+ var sOrientation = oNewOrientation.landscape ? "landscape" : "portrait";
1231
+ Log.debug("BarcodeScanner.orientationChangeListener: device orientation changed to " + sOrientation + ", call openCamera again to resize");
1232
+ if (oBarcodeOverlayDOM) {
1233
+ // hide overlay during orientation change
1234
+ oBarcodeOverlayDOM.hidden = true;
1235
+ }
1236
+ // close the camera since video screen is not in full size after orientation changed
1237
+ closeScannerContain(false);
1238
+ if (Device.os.ios || Device.os.macintosh) {
1239
+ // on iOS devices (iphone and ipad), the dialog may be in small size and moved to top left after orientation changed, so max size and reposition it in center
1240
+ oScanDialog._positionDialog();
1241
+ }
1242
+ // need to wait for the orientation change finished, then reopen camera so that the video screen is in full size
1243
+ setTimeout(function() {
1244
+ openCamera(false);
1245
+ }, 500);
1246
+ }
1247
+
1248
+ /**
1249
+ * Calculate video height and width
1250
+ * @returns {object} Video height and width object
1251
+ * @private
1252
+ */
1253
+ function calculateVideoResolution() {
1254
+ var iAvailHeight = oBarcodeScannerUIContainer.getDomRef().clientHeight,
1255
+ iAvailWidth = oBarcodeScannerUIContainer.getDomRef().clientWidth,
1256
+ iWidth = 1920,
1257
+ iHeight = 1440;
1258
+ /*
1259
+ if (iAvailHeight > iAvailWidth) {
1260
+ iHeight = 1920;
1261
+ iWidth = Math.trunc(1920 * iAvailWidth / iAvailHeight);
1262
+ } else {
1263
+ iWidth = 1920;
1264
+ iHeight = Math.trunc(1920 * iAvailHeight / iAvailWidth);
1265
+ }*/
1266
+ // in portrait mode, width means height ???, so above codes will meet Not Full Screen issue when in this mode
1267
+ // have to change to below, need to check document
1268
+ if (iAvailHeight > iAvailWidth) {
1269
+ iHeight = Math.trunc(1920 * iAvailWidth / iAvailHeight);
1270
+ } else {
1271
+ iHeight = Math.trunc(1920 * iAvailHeight / iAvailWidth);
1272
+ }
1273
+ return {
1274
+ width: { ideal: iWidth },
1275
+ height: { ideal: iHeight }
1276
+ };
1277
+ }
1278
+
1193
1279
  function scanFrame() {
1194
- if (!oScanDialog || !oBarcodeCanvasDOM) {
1280
+ Log.debug("BarcodeScanner.scanFrame: start to set up overlay dom");
1281
+ if (!oScanDialog || !oBarcodeVideoDOM || !oBarcodeVideoDOM.videoHeight || !oBarcodeVideoDOM.videoWidth) {
1282
+ Log.debug("BarcodeScanner.scanFrame: scan dialog or video screen is closed, stop set up");
1195
1283
  return;
1196
1284
  }
1197
1285
  var iInactiveZonePercent = 0.15;
1198
- var oBarcodeScannerUIContainer = oScanDialog.getContent()[0];
1199
1286
 
1200
1287
  if (!oBarcodeOverlayDOM && oBarcodeScannerUIContainer) {
1201
1288
  oBarcodeOverlayDOM = oBarcodeScannerUIContainer.getDomRef('overlay');
1202
1289
  }
1203
1290
 
1204
- updateZoom();
1205
-
1206
1291
  if (oBarcodeOverlayDOM) {
1207
- var oBarcodeOverlayWidthTemp = oBarcodeCanvasDOM.clientWidth * (1 - 2 * iInactiveZonePercent);
1208
- var oBarcodeOverlayHeightTemp = oBarcodeCanvasDOM.clientHeight * (1 - 2 * iInactiveZonePercent);
1292
+ // show overlay since it may be hidden during orientation change
1293
+ oBarcodeOverlayDOM.hidden = false;
1294
+ var iBarcodeVideoDOMWidth = oBarcodeVideoDOM.clientWidth,
1295
+ iBarcodeVideoDOMHeight = oBarcodeVideoDOM.clientHeight;
1296
+ var oBarcodeOverlayWidthTemp = iBarcodeVideoDOMWidth * (1 - 2 * iInactiveZonePercent);
1297
+ var oBarcodeOverlayHeightTemp = iBarcodeVideoDOMHeight * (1 - 2 * iInactiveZonePercent);
1298
+
1209
1299
 
1210
1300
  if (oBarcodeOverlayWidthTemp <= oBarcodeOverlayHeightTemp) {
1211
1301
  oBarcodeOverlayHeightTemp = oBarcodeOverlayWidthTemp * (1 - 2 * iInactiveZonePercent);
@@ -1219,73 +1309,23 @@ sap.ui.define([
1219
1309
 
1220
1310
  oBarcodeOverlayDOM.style.width = oBarcodeOverlayWidthTemp + 'px';
1221
1311
  oBarcodeOverlayDOM.style.height = oBarcodeOverlayHeightTemp + 'px';
1222
- oBarcodeOverlayDOM.style.borderWidth = (oBarcodeCanvasDOM.clientHeight - oBarcodeOverlayHeightTemp) / 2 + 'px ' + (oBarcodeCanvasDOM.clientWidth - oBarcodeOverlayWidthTemp) / 2 + 'px';
1223
- }
1224
- }
1225
- }
1226
-
1227
- function updateZoom() {
1228
- if (oModel.getProperty("/config/zoom") !== "skipUpdateZoom" && oBarcodeVideoDOM) {
1229
- var videoTrack = oBarcodeVideoDOM.srcObject.getVideoTracks();
1230
- var oSupport = window.navigator.mediaDevices.getSupportedConstraints();
1231
- var capabilities = videoTrack[0].getCapabilities();
1232
- // Verify the permission about updating zoom
1233
- if (oSupport.zoom && capabilities && capabilities.zoom) {
1234
- Log.debug("BarcodeScanner.updateZoom: Support zoom to update");
1235
- if (oModel.getProperty("/config/zoom") === 'undefined' || oModel.getProperty("/config/zoom") === null) {
1236
- // reset zoom
1237
- oModel.setProperty("/config/zoom", capabilities.zoom.min);
1238
- }
1239
- } else {
1240
- Log.debug("BarcodeScanner.updateZoom: Don't support zoom or getCapabilities() failed.");
1241
- oModel.setProperty("/config/zoom", "skipUpdateZoom");
1242
- return;
1243
- }
1244
- // Update zoom
1245
- try {
1246
- var fRoom = oModel.getProperty("/config/zoom");
1247
- videoTrack[0].applyConstraints(
1248
- {
1249
- advanced: [{
1250
- zoom: fRoom
1251
- }]
1252
- }
1253
- ).then(
1254
- function() {
1255
- oModel.setProperty("/config/zoom", "skipUpdateZoom");
1256
- Log.debug("BarcodeScanner.updateZoom: Zoom is updated to " + fRoom);
1257
- }
1258
- ).catch(
1259
- function(error) {
1260
- if (error && error.message && error.message.match(/out of range|Failed to read the 'zoom' property/i)) {
1261
- oModel.setProperty("/config/zoom", "skipUpdateZoom");
1262
- MessageToast.show(
1263
- oResourceModel.getResourceBundle().getText('BARCODE_DIALOG_CAMERA_UPDATE_PARAMETER_ERROR_MSG', 'zoom'),
1264
- {
1265
- duration: 1000
1266
- }
1267
- );
1268
- } else {
1269
- Log.error("BarcodeScanner.updateZoom: Update zoom to " + fRoom + " failed. Error Message:" + error);
1270
- }
1271
- }
1272
- );
1273
- } catch (err) {
1274
- Log.error("BarcodeScanner.updateZoom: applyConstraints() failed. Error Message:" + err);
1275
- oModel.setProperty("/config/zoom", "skipUpdateZoom");
1312
+ oBarcodeOverlayDOM.style.borderWidth = (iBarcodeVideoDOMHeight - oBarcodeOverlayHeightTemp) / 2 + 'px ' + (iBarcodeVideoDOMWidth - oBarcodeOverlayWidthTemp) / 2 + 'px';
1276
1313
  }
1277
- var settings = videoTrack[0].getSettings();
1278
- Log.debug("BarcodeScanner.updateZoom: frameRate is " + settings.frameRate + ". zoom is " + settings.zoom);
1279
1314
  }
1280
1315
  }
1281
1316
 
1282
- function closeScannerContain() {
1317
+ function closeScannerContain(bDetachOrientationChangeListener) {
1283
1318
  // oStream and oBarcodeVideoDOM.srcObject point to the same video stream, set them to undefined when closing scan screen
1319
+ if (oVideoTrack) {
1320
+ oVideoTrack.stop();
1321
+ oVideoTrack = undefined;
1322
+ }
1284
1323
  if (oStream) {
1285
- var videoTrack = typeof oStream.stop === "function" ? oStream : oStream.getTracks()[0];
1286
- videoTrack.stop();
1287
1324
  oStream = undefined;
1288
1325
  }
1326
+ if (Device.support.orientation && bDetachOrientationChangeListener !== false) {
1327
+ Device.orientation.detachHandler(orientationChangeListener);
1328
+ }
1289
1329
  if (oBarcodeVideoDOM && oBarcodeVideoDOM.srcObject) {
1290
1330
  oBarcodeVideoDOM.srcObject = undefined;
1291
1331
  }
@@ -1420,6 +1460,7 @@ sap.ui.define([
1420
1460
  Log.error("BarcodeScanner.scan: Barcode scanning is already in progress.");
1421
1461
  return;
1422
1462
  }
1463
+ Log.debug("BarcodeScanner.scan: start to scan barcode.");
1423
1464
 
1424
1465
  oModel.setProperty("/bReady", false);
1425
1466
  if (typeof fnSuccess === 'function') {
@@ -1459,15 +1500,32 @@ sap.ui.define([
1459
1500
  }
1460
1501
  );
1461
1502
  }
1462
- oModel.setProperty("/config/zoom", zoom);
1503
+ // Reset zoom
1504
+ if (oModel.getProperty("/config/defaultConstraints/video/zoom") !== undefined) {
1505
+ delete oModel.getProperty("/config/defaultConstraints/video").zoom;
1506
+ }
1507
+ // apply value of zoom parameter
1508
+ if (typeof zoom === "number" && zoom > 0) {
1509
+ oModel.setProperty("/config/defaultConstraints/video/zoom", zoom);
1510
+ } else if (typeof zoom !== 'undefined') {
1511
+ MessageToast.show(
1512
+ oResourceModel.getResourceBundle().getText('BARCODE_DIALOG_CAMERA_UPDATE_PARAMETER_ERROR_MSG', 'zoom'),
1513
+ {
1514
+ duration: 1000
1515
+ }
1516
+ );
1517
+ }
1463
1518
  oModel.setProperty("/scanDialog/keepCameraScan", keepCameraScan);
1464
1519
  oModel.checkUpdate(true);
1465
1520
 
1466
1521
  if (checkZebraEBScanAvailable()) {
1522
+ Log.debug("BarcodeScanner.scan: Zebra EB is available, use it to scan barcode.");
1467
1523
  scanWithZebra();
1468
1524
  } else if (isScannerAPIAvailable("Cordova")) {
1525
+ Log.debug("BarcodeScanner.scan: Cordova is available, use it to scan barcode.");
1469
1526
  scanWithCordova();
1470
1527
  } else {
1528
+ Log.debug("BarcodeScanner.scan: both of Zebra EB and Cordova are NOT available, use ZXingCPP to scan barcode.");
1471
1529
  scanWithZXingCPP();
1472
1530
  }
1473
1531
  };
@@ -1569,7 +1627,7 @@ sap.ui.define([
1569
1627
  Log.error("BarcodeScanner.scan: The scanner API '" + scannerAPI + "' is unavailable, will use current scanner API '" + oModel.getProperty("/apis/" + getCurrentScannerAPI() + "/description") + "' to scan the barcode.");
1570
1628
  return false;
1571
1629
  } else {
1572
- Log.info("BarcodeScanner.scan: Switch to scanner API '" + scannerAPI + "' to scan the barcode.");
1630
+ Log.debug("BarcodeScanner.scan: Switch to scanner API '" + scannerAPI + "' to scan the barcode.");
1573
1631
  setCurrentScannerAPI(scannerAPI);
1574
1632
  return true;
1575
1633
  }
@@ -1577,7 +1635,7 @@ sap.ui.define([
1577
1635
  Log.error("BarcodeScanner.scan: The scanner API '" + scannerAPI + "' is unavailable, will use current scanner API '" + oModel.getProperty("/apis/" + getCurrentScannerAPI() + "/description") + "' to scan the barcode.");
1578
1636
  return false;
1579
1637
  } else {
1580
- Log.info("BarcodeScanner.scan: Switch to scanner API '" + scannerAPI + "' to scan the barcode.");
1638
+ Log.debug("BarcodeScanner.scan: Switch to scanner API '" + scannerAPI + "' to scan the barcode.");
1581
1639
  setCurrentScannerAPI(scannerAPI);
1582
1640
  return true;
1583
1641
  }
@@ -24,10 +24,13 @@ sap.ui.define([
24
24
  oRm.openStart("div", oControl);
25
25
  oRm.class("sapNdcRTCDialogVideo");
26
26
  oRm.openEnd();
27
- oRm.openStart("canvas", oControl.getId() + "-canvas");
27
+ oRm.openStart("video", oControl.getId() + "-video");
28
+ oRm.attr("autoplay", "autoplay");
29
+ oRm.attr("webkit-playsinline", "webkit-playsinline");
30
+ oRm.attr("playsinline", "playsinline");
28
31
  oRm.class("sapNdcRTCDialogVideoContainer");
29
32
  oRm.openEnd();
30
- oRm.close("canvas");
33
+ oRm.close("video");
31
34
  oRm.close("div");
32
35
 
33
36
  // Overlay that is used to mark scan area
@@ -28,7 +28,6 @@
28
28
  .sapNdcRTCDialogVideo .sapNdcRTCDialogVideoContainer {
29
29
  width: 100%;
30
30
  height: 100%;
31
- object-fit: cover;
32
31
  }
33
32
 
34
33
  .sapNdcRTCDialogOverlay .sapNdcRTCDialogOverlayBox {
@@ -32,7 +32,7 @@ sap.ui.define(['sap/m/library', 'sap/ui/core/library'],
32
32
  ],
33
33
  elements: [],
34
34
  noLibraryCSS: true,
35
- version: "1.96.24"
35
+ version: "1.96.25"
36
36
  });
37
37
 
38
38
  return sap.ndc;
@@ -1,20 +1,32 @@
1
+ #This is the resource bundle for the sap.ndc library
2
+ #
1
3
 
4
+ #XTIT: title of the manual barcode input
2
5
  BARCODE_DIALOG_TITLE=Enter Barcode
3
6
 
7
+ #XBUT: OK button in the manual barcode input dialog
4
8
  BARCODE_DIALOG_OK=OK
5
9
 
10
+ #XBUT: Cancel button in the manual barcode input dialog
6
11
  BARCODE_DIALOG_CANCEL=Cancel
7
12
 
13
+ #XFLD: Placeholder of the barcode input field
8
14
  BARCODE_DIALOG_PLACEHOLDER=Enter barcode
9
15
 
16
+ #YMSG: Message in the manual barcode input dialog
10
17
  BARCODE_DIALOG_MSG=Scanner is not available
11
18
 
19
+ #XMSG: error message for updating parameter of Camera
12
20
  BARCODE_DIALOG_CAMERA_UPDATE_PARAMETER_ERROR_MSG=The {0} parameter is out of range.
13
21
 
22
+ #XTIT: title of the scan barcode dialog
14
23
  BARCODE_DIALOG_SCANNING_TITLE=Scan Barcode
15
24
 
25
+ #XTOL: Barcode Scanner Button tooltip
16
26
  BARCODE_SCANNER_BUTTON_TOOLTIP=Bar Code Scanner Button
17
27
 
28
+ #XTIT: title of the scan bar busy dialog
18
29
  BARCODE_DIALOG_BUSY_TITLE=Loading Libraries
19
30
 
31
+ #XTXT: text of loading zxing-cpp in the scan bar busy dialog
20
32
  BARCODE_DIALOG_BUSY_TEXT_ZXINGCPP=Loading ZXing-cpp library...
@@ -13,7 +13,7 @@ BARCODE_DIALOG_CAMERA_UPDATE_PARAMETER_ERROR_MSG=Parametar {0} je van raspona.
13
13
 
14
14
  BARCODE_DIALOG_SCANNING_TITLE=Skeniraj bar kod
15
15
 
16
- BARCODE_SCANNER_BUTTON_TOOLTIP=Bar Code Scanner Button
16
+ BARCODE_SCANNER_BUTTON_TOOLTIP=Dugme skenera bar koda
17
17
 
18
18
  BARCODE_DIALOG_BUSY_TITLE=U\u010Ditavanje biblioteka
19
19
 
@@ -13,7 +13,7 @@ BARCODE_DIALOG_CAMERA_UPDATE_PARAMETER_ERROR_MSG=\u041F\u0430\u0440\u0430\u043C\
13
13
 
14
14
  BARCODE_DIALOG_SCANNING_TITLE=\u0421\u043A\u0435\u043D\u0438\u0440\u0430\u0458 \u0431\u0430\u0440 \u043A\u043E\u0434
15
15
 
16
- BARCODE_SCANNER_BUTTON_TOOLTIP=Bar Code Scanner Button
16
+ BARCODE_SCANNER_BUTTON_TOOLTIP=\u0414\u0443\u0433\u043C\u0435 \u0441\u043A\u0435\u043D\u0435\u0440\u0430 \u0431\u0430\u0440 \u043A\u043E\u0434\u0430
17
17
 
18
18
  BARCODE_DIALOG_BUSY_TITLE=\u0423\u0447\u0438\u0442\u0430\u0432\u0430\u045A\u0435 \u0431\u0438\u0431\u043B\u0438\u043E\u0442\u0435\u043A\u0430
19
19