image-js 0.35.2 → 0.35.4

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.
Files changed (170) hide show
  1. package/index.d.ts +3 -10
  2. package/lib/browser/environment.js +0 -6
  3. package/lib/browser/worker/extend.js +0 -3
  4. package/lib/browser/worker/process/background.js +0 -12
  5. package/lib/browser/worker/worker.js +0 -17
  6. package/lib/image/Image.js +18 -51
  7. package/lib/image/compute/colorHistogram.js +0 -8
  8. package/lib/image/compute/countAlphaPixels.js +0 -3
  9. package/lib/image/compute/extendedPoints.js +2 -7
  10. package/lib/image/compute/histogram.js +6 -25
  11. package/lib/image/compute/localMaxima.js +2 -10
  12. package/lib/image/compute/max.js +0 -5
  13. package/lib/image/compute/mean.js +0 -4
  14. package/lib/image/compute/median.js +0 -4
  15. package/lib/image/compute/min.js +0 -5
  16. package/lib/image/compute/minimalBoundingRectangle.js +5 -18
  17. package/lib/image/compute/moment.js +0 -3
  18. package/lib/image/compute/monotoneChainConvexHull.js +0 -3
  19. package/lib/image/compute/points.js +0 -3
  20. package/lib/image/compute/relativePosition.js +2 -8
  21. package/lib/image/compute/sum.js +0 -5
  22. package/lib/image/core/bitMethods.js +0 -11
  23. package/lib/image/core/checkProcessable.js +0 -13
  24. package/lib/image/core/environment.js +0 -8
  25. package/lib/image/core/export.js +0 -38
  26. package/lib/image/core/extend.js +0 -13
  27. package/lib/image/core/getRGBAData.js +0 -15
  28. package/lib/image/core/kind.js +4 -28
  29. package/lib/image/core/kindNames.js +1 -0
  30. package/lib/image/core/load.js +1 -53
  31. package/lib/image/core/mediaTypes.js +0 -2
  32. package/lib/image/core/valueMethods.js +0 -13
  33. package/lib/image/extend.js +7 -83
  34. package/lib/image/filter/abs.js +0 -3
  35. package/lib/image/filter/add.js +2 -8
  36. package/lib/image/filter/background.js +0 -9
  37. package/lib/image/filter/blurFilter.js +0 -6
  38. package/lib/image/filter/divide.js +0 -8
  39. package/lib/image/filter/flipX.js +0 -5
  40. package/lib/image/filter/flipY.js +0 -4
  41. package/lib/image/filter/gaussianFilter.js +0 -5
  42. package/lib/image/filter/gradientFilter.js +0 -11
  43. package/lib/image/filter/hypotenuse.js +0 -13
  44. package/lib/image/filter/invert.js +0 -9
  45. package/lib/image/filter/level.js +1 -19
  46. package/lib/image/filter/medianFilter.js +0 -15
  47. package/lib/image/filter/multiply.js +0 -10
  48. package/lib/image/filter/scharrFilter.js +0 -4
  49. package/lib/image/filter/sobelFilter.js +0 -4
  50. package/lib/image/filter/subtract.js +0 -8
  51. package/lib/image/filter/subtractImage.js +0 -10
  52. package/lib/image/internal/checks.js +1 -9
  53. package/lib/image/internal/clamp.js +0 -1
  54. package/lib/image/internal/copy.js +0 -2
  55. package/lib/image/internal/copyAlphaChannel.js +0 -1
  56. package/lib/image/internal/getImageParameters.js +0 -1
  57. package/lib/image/internal/getOutputImage.js +1 -13
  58. package/lib/image/model/model.js +1 -1
  59. package/lib/image/morphology/blackHat.js +0 -5
  60. package/lib/image/morphology/close.js +0 -5
  61. package/lib/image/morphology/dilate.js +0 -40
  62. package/lib/image/morphology/erode.js +0 -40
  63. package/lib/image/morphology/morphologicalGradient.js +0 -5
  64. package/lib/image/morphology/open.js +0 -5
  65. package/lib/image/morphology/topHat.js +0 -5
  66. package/lib/image/operator/cannyEdge.js +0 -3
  67. package/lib/image/operator/convolution.js +9 -34
  68. package/lib/image/operator/convolutionSeparable.js +0 -10
  69. package/lib/image/operator/extract.js +4 -13
  70. package/lib/image/operator/floodFill.js +2 -15
  71. package/lib/image/operator/getSeparatedKernel.js +0 -2
  72. package/lib/image/operator/paintLabels.js +2 -13
  73. package/lib/image/operator/paintMasks.js +2 -12
  74. package/lib/image/operator/paintPoints.js +0 -9
  75. package/lib/image/operator/paintPolygon.js +0 -14
  76. package/lib/image/operator/paintPolygons.js +0 -4
  77. package/lib/image/operator/paintPolyline.js +0 -7
  78. package/lib/image/operator/paintPolylines.js +0 -4
  79. package/lib/image/roi/Roi.js +27 -208
  80. package/lib/image/roi/RoiLayer.js +1 -22
  81. package/lib/image/roi/RoiMap.js +5 -38
  82. package/lib/image/roi/creator/fromMask.js +4 -22
  83. package/lib/image/roi/creator/fromMaskConnectedComponentLabelingAlgorithm.js +2 -20
  84. package/lib/image/roi/creator/fromMaxima.js +10 -43
  85. package/lib/image/roi/creator/fromPoints.js +2 -10
  86. package/lib/image/roi/creator/fromWaterShed.js +6 -17
  87. package/lib/image/roi/feretDiameters.js +9 -21
  88. package/lib/image/roi/manager.js +30 -119
  89. package/lib/image/roi/util/commonBorderLength.js +5 -16
  90. package/lib/image/roi/util/mergeRoi.js +2 -21
  91. package/lib/image/transform/cmyk.js +0 -9
  92. package/lib/image/transform/colorDepth.js +0 -12
  93. package/lib/image/transform/crop.js +0 -20
  94. package/lib/image/transform/cropAlpha.js +0 -11
  95. package/lib/image/transform/grey.js +0 -17
  96. package/lib/image/transform/greyAlgorithms.js +1 -24
  97. package/lib/image/transform/hsl.js +0 -16
  98. package/lib/image/transform/hsv.js +0 -15
  99. package/lib/image/transform/insert.js +0 -6
  100. package/lib/image/transform/mask/huang.js +3 -18
  101. package/lib/image/transform/mask/intermodes.js +3 -14
  102. package/lib/image/transform/mask/isodata.js +0 -14
  103. package/lib/image/transform/mask/li.js +12 -42
  104. package/lib/image/transform/mask/mask.js +1 -13
  105. package/lib/image/transform/mask/maxEntropy.js +8 -25
  106. package/lib/image/transform/mask/mean.js +1 -3
  107. package/lib/image/transform/mask/minError.js +10 -21
  108. package/lib/image/transform/mask/minimum.js +0 -20
  109. package/lib/image/transform/mask/moments.js +4 -17
  110. package/lib/image/transform/mask/otsu.js +1 -7
  111. package/lib/image/transform/mask/percentile.js +0 -8
  112. package/lib/image/transform/mask/renyiEntropy.js +8 -34
  113. package/lib/image/transform/mask/shanbhag.js +8 -25
  114. package/lib/image/transform/mask/thresholdAlgorithms.js +1 -17
  115. package/lib/image/transform/mask/triangle.js +13 -29
  116. package/lib/image/transform/mask/yen.js +2 -14
  117. package/lib/image/transform/pad.js +0 -20
  118. package/lib/image/transform/resize/nearestNeighbor.js +0 -6
  119. package/lib/image/transform/resize/resize.js +0 -16
  120. package/lib/image/transform/rgba.js +0 -9
  121. package/lib/image/transform/rgba8.js +0 -3
  122. package/lib/image/transform/rotate.js +0 -29
  123. package/lib/image/transform/rotateFree.js +0 -31
  124. package/lib/image/transform/warping.js +2 -35
  125. package/lib/image/utility/combineChannels.js +0 -11
  126. package/lib/image/utility/getBestMatch.js +2 -13
  127. package/lib/image/utility/getChannel.js +0 -10
  128. package/lib/image/utility/getClosestCommonParent.js +6 -23
  129. package/lib/image/utility/getColumn.js +0 -4
  130. package/lib/image/utility/getIntersection.js +2 -18
  131. package/lib/image/utility/getMatrix.js +0 -7
  132. package/lib/image/utility/getPixelsArray.js +0 -5
  133. package/lib/image/utility/getPixelsGrid.js +0 -11
  134. package/lib/image/utility/getRow.js +0 -4
  135. package/lib/image/utility/getSimilarity.js +3 -17
  136. package/lib/image/utility/getThreshold.js +0 -4
  137. package/lib/image/utility/setBorder.js +0 -16
  138. package/lib/image/utility/setChannel.js +0 -6
  139. package/lib/image/utility/setMatrix.js +3 -6
  140. package/lib/image/utility/split.js +2 -15
  141. package/lib/index.js +0 -12
  142. package/lib/kernel/kernel.js +0 -3
  143. package/lib/kernel/laplacianOfGaussian.js +1 -7
  144. package/lib/node_modules/test/binary.js +0 -3
  145. package/lib/node_modules/test/oneRoi.js +0 -2
  146. package/lib/stack/Stack.js +2 -35
  147. package/lib/stack/compute/histogram.js +0 -4
  148. package/lib/stack/compute/histograms.js +0 -4
  149. package/lib/stack/compute/max.js +0 -3
  150. package/lib/stack/compute/median.js +0 -4
  151. package/lib/stack/compute/min.js +0 -3
  152. package/lib/stack/extend.js +1 -11
  153. package/lib/stack/transform/matchAndCrop.js +6 -19
  154. package/lib/stack/utility/averageImage.js +0 -9
  155. package/lib/stack/utility/maxImage.js +0 -7
  156. package/lib/stack/utility/minImage.js +0 -7
  157. package/lib/util/Shape.js +3 -40
  158. package/lib/util/base64.js +3 -14
  159. package/lib/util/channel.js +1 -35
  160. package/lib/util/color.js +1 -25
  161. package/lib/util/converter.js +1 -13
  162. package/lib/util/deepValue.js +0 -3
  163. package/lib/util/histogram.js +1 -12
  164. package/lib/util/kernel.js +2 -12
  165. package/lib/util/matrix.js +0 -13
  166. package/lib/util/points.js +12 -35
  167. package/lib/util/value.js +0 -7
  168. package/lib/util/zerosMatrix.js +0 -3
  169. package/package.json +1 -1
  170. package/src/image/utility/setMatrix.js +4 -0
@@ -4,17 +4,11 @@ Object.defineProperty(exports, "__esModule", {
4
4
  value: true
5
5
  });
6
6
  exports.default = resize;
7
-
8
7
  var _converter = require("../../../util/converter");
9
-
10
8
  var _Image = _interopRequireDefault(require("../../Image"));
11
-
12
9
  var _checks = require("../../internal/checks");
13
-
14
10
  var _nearestNeighbor = _interopRequireDefault(require("./nearestNeighbor"));
15
-
16
11
  function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
17
-
18
12
  /**
19
13
  * Resize an image
20
14
  * @memberof Image
@@ -36,7 +30,6 @@ function resize(options = {}) {
36
30
  const interpolationToUse = (0, _checks.checkInterpolation)(interpolation);
37
31
  let width = options.width;
38
32
  let height = options.height;
39
-
40
33
  if (!width) {
41
34
  if (height && preserveAspectRatio) {
42
35
  width = Math.round(height * (this.width / this.height));
@@ -44,7 +37,6 @@ function resize(options = {}) {
44
37
  width = this.width;
45
38
  }
46
39
  }
47
-
48
40
  if (!height) {
49
41
  if (preserveAspectRatio) {
50
42
  height = Math.round(width * (this.height / this.width));
@@ -52,36 +44,28 @@ function resize(options = {}) {
52
44
  height = this.height;
53
45
  }
54
46
  }
55
-
56
47
  ({
57
48
  width,
58
49
  height
59
50
  } = (0, _converter.factorDimensions)(factor, width, height));
60
-
61
51
  if (width === this.width && height === this.height) {
62
52
  const newImage = this.clone();
63
53
  newImage.position = [0, 0];
64
54
  return newImage;
65
55
  }
66
-
67
56
  let shiftX = Math.round((this.width - width) / 2);
68
57
  let shiftY = Math.round((this.height - height) / 2);
69
-
70
58
  const newImage = _Image.default.createFrom(this, {
71
59
  width,
72
60
  height,
73
61
  position: [shiftX, shiftY]
74
62
  });
75
-
76
63
  switch (interpolationToUse) {
77
64
  case _checks.validInterpolations.nearestneighbor:
78
65
  _nearestNeighbor.default.call(this, newImage, width, height);
79
-
80
66
  break;
81
-
82
67
  default:
83
68
  throw new Error(`unsupported resize interpolation: ${interpolationToUse}`);
84
69
  }
85
-
86
70
  return newImage;
87
71
  }
@@ -4,13 +4,9 @@ Object.defineProperty(exports, "__esModule", {
4
4
  value: true
5
5
  });
6
6
  exports.default = rgba;
7
-
8
7
  var _Image = _interopRequireDefault(require("../Image"));
9
-
10
8
  var _model = require("../model/model");
11
-
12
9
  function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
13
-
14
10
  /**
15
11
  * Make a copy of the current image and convert to RGBA
16
12
  * The source image must have RGB color model, 8 or 16 bits.
@@ -28,18 +24,14 @@ function rgba() {
28
24
  alpha: [0, 1],
29
25
  colorModel: [_model.RGB]
30
26
  });
31
-
32
27
  if (this.colorModel === _model.RGB && this.alpha) {
33
28
  return this.clone();
34
29
  }
35
-
36
30
  let newImage = _Image.default.createFrom(this, {
37
31
  alpha: 1
38
32
  });
39
-
40
33
  let ptr = 0;
41
34
  let data = this.data;
42
-
43
35
  for (let i = 0; i < data.length; i += this.channels) {
44
36
  newImage.data[ptr++] = data[i];
45
37
  newImage.data[ptr++] = data[i + 1];
@@ -47,6 +39,5 @@ function rgba() {
47
39
  newImage.data[ptr++] = this.maxValue;
48
40
  ptr++;
49
41
  }
50
-
51
42
  return newImage;
52
43
  }
@@ -4,11 +4,8 @@ Object.defineProperty(exports, "__esModule", {
4
4
  value: true
5
5
  });
6
6
  exports.default = rgba8;
7
-
8
7
  var _Image = _interopRequireDefault(require("../Image"));
9
-
10
8
  function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
11
-
12
9
  /**
13
10
  * Make a copy of the current image and convert to RGBA 8 bits
14
11
  * Those images are the one that are displayed in a canvas.
@@ -6,13 +6,9 @@ Object.defineProperty(exports, "__esModule", {
6
6
  exports.rotate = rotate;
7
7
  exports.rotateLeft = rotateLeft;
8
8
  exports.rotateRight = rotateRight;
9
-
10
9
  var _Image = _interopRequireDefault(require("../Image"));
11
-
12
10
  var _rotateFree = _interopRequireDefault(require("./rotateFree"));
13
-
14
11
  function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
15
-
16
12
  /**
17
13
  * Rotates an image.
18
14
  * @memberof Image
@@ -26,28 +22,21 @@ function rotate(angle, options) {
26
22
  this.checkProcessable('rotate', {
27
23
  bitDepth: [1, 8, 16]
28
24
  });
29
-
30
25
  if (typeof angle !== 'number') {
31
26
  throw new TypeError('angle must be a number');
32
27
  }
33
-
34
28
  if (angle < 0) {
35
29
  angle = Math.ceil(-angle / 360) * 360 + angle;
36
30
  }
37
-
38
31
  switch (angle % 360) {
39
32
  case 0:
40
33
  return this.clone();
41
-
42
34
  case 90:
43
35
  return rotateRight.call(this);
44
-
45
36
  case 180:
46
37
  return rotate180.call(this);
47
-
48
38
  case 270:
49
39
  return rotateLeft.call(this);
50
-
51
40
  default:
52
41
  return _rotateFree.default.call(this, angle, options);
53
42
  }
@@ -59,7 +48,6 @@ function rotate(angle, options) {
59
48
  * @return {Image} The new rotated image
60
49
  */
61
50
 
62
-
63
51
  function rotateLeft() {
64
52
  if (this.bitDepth === 1) {
65
53
  const newImage = new _Image.default(this.height, this.width, {
@@ -67,7 +55,6 @@ function rotateLeft() {
67
55
  parent: this
68
56
  });
69
57
  const newMaxHeight = newImage.height - 1;
70
-
71
58
  for (let i = 0; i < this.height; i++) {
72
59
  for (let j = 0; j < this.width; j++) {
73
60
  if (this.getBitXY(j, i)) {
@@ -75,16 +62,13 @@ function rotateLeft() {
75
62
  }
76
63
  }
77
64
  }
78
-
79
65
  return newImage;
80
66
  } else {
81
67
  const newImage = _Image.default.createFrom(this, {
82
68
  width: this.height,
83
69
  height: this.width
84
70
  });
85
-
86
71
  const newMaxHeight = newImage.height - 1;
87
-
88
72
  for (let i = 0; i < this.height; i++) {
89
73
  for (let j = 0; j < this.width; j++) {
90
74
  for (let k = 0; k < this.channels; k++) {
@@ -92,7 +76,6 @@ function rotateLeft() {
92
76
  }
93
77
  }
94
78
  }
95
-
96
79
  return newImage;
97
80
  }
98
81
  }
@@ -103,7 +86,6 @@ function rotateLeft() {
103
86
  * @return {Image} The new rotated image
104
87
  */
105
88
 
106
-
107
89
  function rotateRight() {
108
90
  if (this.bitDepth === 1) {
109
91
  const newImage = new _Image.default(this.height, this.width, {
@@ -111,7 +93,6 @@ function rotateRight() {
111
93
  parent: this
112
94
  });
113
95
  const newMaxWidth = newImage.width - 1;
114
-
115
96
  for (let i = 0; i < this.height; i++) {
116
97
  for (let j = 0; j < this.width; j++) {
117
98
  if (this.getBitXY(j, i)) {
@@ -119,16 +100,13 @@ function rotateRight() {
119
100
  }
120
101
  }
121
102
  }
122
-
123
103
  return newImage;
124
104
  } else {
125
105
  const newImage = _Image.default.createFrom(this, {
126
106
  width: this.height,
127
107
  height: this.width
128
108
  });
129
-
130
109
  const newMaxWidth = newImage.width - 1;
131
-
132
110
  for (let i = 0; i < this.height; i++) {
133
111
  for (let j = 0; j < this.width; j++) {
134
112
  for (let k = 0; k < this.channels; k++) {
@@ -136,11 +114,9 @@ function rotateRight() {
136
114
  }
137
115
  }
138
116
  }
139
-
140
117
  return newImage;
141
118
  }
142
119
  }
143
-
144
120
  function rotate180() {
145
121
  if (this.bitDepth === 1) {
146
122
  const newImage = new _Image.default(this.width, this.height, {
@@ -149,7 +125,6 @@ function rotate180() {
149
125
  });
150
126
  const newMaxWidth = newImage.width - 1;
151
127
  const newMaxHeight = newImage.height - 1;
152
-
153
128
  for (let i = 0; i < this.height; i++) {
154
129
  for (let j = 0; j < this.width; j++) {
155
130
  if (this.getBitXY(j, i)) {
@@ -157,14 +132,11 @@ function rotate180() {
157
132
  }
158
133
  }
159
134
  }
160
-
161
135
  return newImage;
162
136
  } else {
163
137
  const newImage = _Image.default.createFrom(this);
164
-
165
138
  const newMaxWidth = newImage.width - 1;
166
139
  const newMaxHeight = newImage.height - 1;
167
-
168
140
  for (let i = 0; i < this.height; i++) {
169
141
  for (let j = 0; j < this.width; j++) {
170
142
  for (let k = 0; k < this.channels; k++) {
@@ -172,7 +144,6 @@ function rotate180() {
172
144
  }
173
145
  }
174
146
  }
175
-
176
147
  return newImage;
177
148
  }
178
149
  }
@@ -4,24 +4,18 @@ Object.defineProperty(exports, "__esModule", {
4
4
  value: true
5
5
  });
6
6
  exports.default = rotateFree;
7
-
8
7
  var _Image = _interopRequireDefault(require("../Image"));
9
-
10
8
  var _checks = require("../internal/checks");
11
-
12
9
  function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
13
-
14
10
  function rotateFree(degrees, options = {}) {
15
11
  const {
16
12
  interpolation = _checks.validInterpolations.nearestneighbor,
17
13
  width = this.width,
18
14
  height = this.height
19
15
  } = options;
20
-
21
16
  if (typeof degrees !== 'number') {
22
17
  throw new TypeError('degrees must be a number');
23
18
  }
24
-
25
19
  const interpolationToUse = (0, _checks.checkInterpolation)(interpolation);
26
20
  const radians = degrees * Math.PI / 180;
27
21
  const newWidth = Math.floor(Math.abs(width * Math.cos(radians)) + Math.abs(height * Math.sin(radians)));
@@ -30,10 +24,8 @@ function rotateFree(degrees, options = {}) {
30
24
  const sin = Math.sin(-radians);
31
25
  let x0 = newWidth / 2;
32
26
  let y0 = newHeight / 2;
33
-
34
27
  if (newWidth % 2 === 0) {
35
28
  x0 = x0 - 0.5;
36
-
37
29
  if (newHeight % 2 === 0) {
38
30
  y0 = y0 - 0.5;
39
31
  } else {
@@ -41,30 +33,24 @@ function rotateFree(degrees, options = {}) {
41
33
  }
42
34
  } else {
43
35
  x0 = Math.floor(x0);
44
-
45
36
  if (newHeight % 2 === 0) {
46
37
  y0 = y0 - 0.5;
47
38
  } else {
48
39
  y0 = Math.floor(y0);
49
40
  }
50
41
  }
51
-
52
42
  const incrementX = Math.floor(width / 2 - x0);
53
43
  const incrementY = Math.floor(height / 2 - y0);
54
-
55
44
  if (this.bitDepth === 1) {
56
45
  const newImage = new _Image.default(newWidth, newHeight, {
57
46
  kind: 'BINARY',
58
47
  parent: this
59
48
  });
60
-
61
49
  switch (interpolationToUse) {
62
50
  case _checks.validInterpolations.nearestneighbor:
63
51
  return rotateBinaryNearestNeighbor(this, newImage, incrementX, incrementY, x0, y0, cos, sin);
64
-
65
52
  case _checks.validInterpolations.bilinear:
66
53
  return rotateBinaryBilinear(this, newImage, incrementX, incrementY, x0, y0, cos, sin);
67
-
68
54
  default:
69
55
  throw new Error(`unsupported rotate interpolation: ${interpolationToUse}`);
70
56
  }
@@ -73,27 +59,22 @@ function rotateFree(degrees, options = {}) {
73
59
  width: newWidth,
74
60
  height: newHeight
75
61
  });
76
-
77
62
  switch (interpolationToUse) {
78
63
  case _checks.validInterpolations.nearestneighbor:
79
64
  return rotateNearestNeighbor(this, newImage, incrementX, incrementY, x0, y0, cos, sin);
80
-
81
65
  case _checks.validInterpolations.bilinear:
82
66
  return rotateBilinear(this, newImage, incrementX, incrementY, x0, y0, cos, sin);
83
-
84
67
  default:
85
68
  throw new Error(`unsupported rotate interpolation: ${interpolationToUse}`);
86
69
  }
87
70
  }
88
71
  }
89
-
90
72
  function rotateNearestNeighbor(thisImage, newImage, incrementX, incrementY, x0, y0, cos, sin) {
91
73
  for (let i = 0; i < newImage.width; i += 1) {
92
74
  for (let j = 0; j < newImage.height; j += 1) {
93
75
  for (let c = 0; c < thisImage.channels; c++) {
94
76
  let x = Math.round((i - x0) * cos - (j - y0) * sin + x0) + incrementX;
95
77
  let y = Math.round((j - y0) * cos + (i - x0) * sin + y0) + incrementY;
96
-
97
78
  if (x < 0 || x >= thisImage.width || y < 0 || y >= thisImage.height) {
98
79
  if (thisImage.alpha === 1 && c === thisImage.channels - 1) {
99
80
  newImage.setValueXY(i, j, c, 0);
@@ -106,28 +87,22 @@ function rotateNearestNeighbor(thisImage, newImage, incrementX, incrementY, x0,
106
87
  }
107
88
  }
108
89
  }
109
-
110
90
  return newImage;
111
91
  }
112
-
113
92
  function rotateBinaryNearestNeighbor(thisImage, newImage, incrementX, incrementY, x0, y0, cos, sin) {
114
93
  for (let i = 0; i < newImage.width; i += 1) {
115
94
  for (let j = 0; j < newImage.height; j += 1) {
116
95
  let x = Math.round((i - x0) * cos - (j - y0) * sin + x0) + incrementX;
117
96
  let y = Math.round((j - y0) * cos + (i - x0) * sin + y0) + incrementY;
118
-
119
97
  if (x < 0 || x >= thisImage.width || y < 0 || y >= thisImage.height || thisImage.getBitXY(x, y)) {
120
98
  newImage.setBitXY(i, j);
121
99
  }
122
100
  }
123
101
  }
124
-
125
102
  return newImage;
126
103
  }
127
-
128
104
  function rotateBilinear(thisImage, newImage, incrementX, incrementY, x0, y0, cos, sin) {
129
105
  let stride = thisImage.width * thisImage.channels;
130
-
131
106
  for (let j = 0; j < newImage.height; j++) {
132
107
  for (let i = 0; i < newImage.width; i++) {
133
108
  let x = (i - x0) * cos - (j - y0) * sin + x0 + incrementX;
@@ -136,7 +111,6 @@ function rotateBilinear(thisImage, newImage, incrementX, incrementY, x0, y0, cos
136
111
  let y1 = y | 0;
137
112
  let xDiff = x - x1;
138
113
  let yDiff = y - y1;
139
-
140
114
  for (let c = 0; c < thisImage.channels; c++) {
141
115
  if (x < 0 || x >= thisImage.width || y < 0 || y >= thisImage.height) {
142
116
  if (thisImage.alpha === 1 && c === thisImage.channels - 1) {
@@ -156,13 +130,10 @@ function rotateBilinear(thisImage, newImage, incrementX, incrementY, x0, y0, cos
156
130
  }
157
131
  }
158
132
  }
159
-
160
133
  return newImage;
161
134
  }
162
-
163
135
  function rotateBinaryBilinear(thisImage, newImage, incrementX, incrementY, x0, y0, cos, sin) {
164
136
  let stride = thisImage.width;
165
-
166
137
  for (let j = 0; j < newImage.height; j++) {
167
138
  for (let i = 0; i < newImage.width; i++) {
168
139
  let x = (i - x0) * cos - (j - y0) * sin + x0 + incrementX;
@@ -171,7 +142,6 @@ function rotateBinaryBilinear(thisImage, newImage, incrementX, incrementY, x0, y
171
142
  let y1 = y | 0;
172
143
  let xDiff = x - x1;
173
144
  let yDiff = y - y1;
174
-
175
145
  if (x < 0 || x >= thisImage.width || y < 0 || y >= thisImage.height) {
176
146
  newImage.setBitXY(i, j);
177
147
  } else {
@@ -185,6 +155,5 @@ function rotateBinaryBilinear(thisImage, newImage, incrementX, incrementY, x0, y
185
155
  }
186
156
  }
187
157
  }
188
-
189
158
  return newImage;
190
159
  }
@@ -4,18 +4,15 @@ Object.defineProperty(exports, "__esModule", {
4
4
  value: true
5
5
  });
6
6
  exports.default = warpingFourPoints;
7
-
8
7
  var _mlMatrix = require("ml-matrix");
9
-
10
8
  var _Image = _interopRequireDefault(require("../Image"));
11
-
12
9
  function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
13
-
14
10
  // REFERENCES :
15
11
  // https://stackoverflow.com/questions/38285229/calculating-aspect-ratio-of-perspective-transform-destination-image/38402378#38402378
16
12
  // http://www.corrmap.com/features/homography_transformation.php
17
13
  // https://ags.cs.uni-kl.de/fileadmin/inf_ags/3dcv-ws11-12/3DCV_WS11-12_lec04.pdf
18
14
  // http://graphics.cs.cmu.edu/courses/15-463/2011_fall/Lectures/morphing.pdf
15
+
19
16
  function order4Points(pts) {
20
17
  let tl = 0;
21
18
  let tr = 0;
@@ -23,28 +20,23 @@ function order4Points(pts) {
23
20
  let bl = 0;
24
21
  let minX = pts[0][0];
25
22
  let indexMinX = 0;
26
-
27
23
  for (let i = 1; i < pts.length; i++) {
28
24
  if (pts[i][0] < minX) {
29
25
  minX = pts[i][0];
30
26
  indexMinX = i;
31
27
  }
32
28
  }
33
-
34
29
  let minX2 = pts[(indexMinX + 1) % pts.length][0];
35
30
  let indexMinX2 = (indexMinX + 1) % pts.length;
36
-
37
31
  for (let i = 1; i < pts.length; i++) {
38
32
  if (pts[i][0] < minX2 && i !== indexMinX) {
39
33
  minX2 = pts[i][0];
40
34
  indexMinX2 = i;
41
35
  }
42
36
  }
43
-
44
37
  if (pts[indexMinX2][1] < pts[indexMinX][1]) {
45
38
  tl = pts[indexMinX2];
46
39
  bl = pts[indexMinX];
47
-
48
40
  if (indexMinX !== (indexMinX2 + 1) % 4) {
49
41
  tr = pts[(indexMinX2 + 1) % 4];
50
42
  br = pts[(indexMinX2 + 2) % 4];
@@ -55,7 +47,6 @@ function order4Points(pts) {
55
47
  } else {
56
48
  bl = pts[indexMinX2];
57
49
  tl = pts[indexMinX];
58
-
59
50
  if (indexMinX2 !== (indexMinX + 1) % 4) {
60
51
  tr = pts[(indexMinX + 1) % 4];
61
52
  br = pts[(indexMinX + 2) % 4];
@@ -64,24 +55,19 @@ function order4Points(pts) {
64
55
  br = pts[(indexMinX + 3) % 4];
65
56
  }
66
57
  }
67
-
68
58
  return [tl, tr, br, bl];
69
59
  }
70
-
71
60
  function distance2Points(p1, p2) {
72
61
  return Math.sqrt(Math.pow(p1[0] - p2[0], 2) + Math.pow(p1[1] - p2[1], 2));
73
62
  }
74
-
75
63
  function crossVect(u, v) {
76
64
  let result = [u[1] * v[2] - u[2] * v[1], u[2] * v[0] - u[0] * v[2], u[0] * v[1] - u[1] * v[0]];
77
65
  return result;
78
66
  }
79
-
80
67
  function dotVect(u, v) {
81
68
  let result = u[0] * v[0] + u[1] * v[1] + u[2] * v[2];
82
69
  return result;
83
70
  }
84
-
85
71
  function computeWidthAndHeigth(tl, tr, br, bl, widthImage, heightImage) {
86
72
  let w = Math.max(distance2Points(tl, tr), distance2Points(bl, br));
87
73
  let h = Math.max(distance2Points(tl, bl), distance2Points(tr, br));
@@ -105,24 +91,18 @@ function computeWidthAndHeigth(tl, tr, br, bl, widthImage, heightImage) {
105
91
  let n32 = n3[1];
106
92
  let n33 = n3[2];
107
93
  let f = 1.0 / (n23 * n33) * (n21 * n31 - (n21 * n33 + n23 * n31) * u0 + n23 * n33 * u0 * u0 + (n22 * n32 - (n22 * n33 + n23 * n32) * v0 + n23 * n33 * v0 * v0));
108
-
109
94
  if (f >= 0) {
110
95
  f = Math.sqrt(f);
111
96
  } else {
112
97
  f = Math.sqrt(-f);
113
98
  }
114
-
115
99
  let A = new _mlMatrix.Matrix([[f, 0, u0], [0, f, v0], [0, 0, 1]]);
116
100
  let At = A.transpose();
117
101
  let Ati = (0, _mlMatrix.inverse)(At);
118
102
  let Ai = (0, _mlMatrix.inverse)(A);
119
-
120
103
  let n2R = _mlMatrix.Matrix.rowVector(n2);
121
-
122
104
  let n3R = _mlMatrix.Matrix.rowVector(n3);
123
-
124
105
  let arReal = Math.sqrt(dotVect(n2R.mmul(Ati).mmul(Ai).to1DArray(), n2) / dotVect(n3R.mmul(Ati).mmul(Ai).to1DArray(), n3));
125
-
126
106
  if (arReal === 0 || arVis === 0) {
127
107
  finalW = Math.ceil(w);
128
108
  finalH = Math.ceil(h);
@@ -133,14 +113,13 @@ function computeWidthAndHeigth(tl, tr, br, bl, widthImage, heightImage) {
133
113
  finalH = Math.ceil(h);
134
114
  finalW = Math.ceil(arReal * finalH);
135
115
  }
136
-
137
116
  return [finalW, finalH];
138
117
  }
139
-
140
118
  function projectionPoint(x, y, a, b, c, d, e, f, g, h, image, channel) {
141
119
  let [newX, newY] = [(a * x + b * y + c) / (g * x + h * y + 1), (d * x + e * y + f) / (g * x + h * y + 1)];
142
120
  return image.getValueXY(Math.floor(newX), Math.floor(newY), channel);
143
121
  }
122
+
144
123
  /**
145
124
  * Transform a quadrilateral into a rectangle
146
125
  * @memberof Image
@@ -155,34 +134,28 @@ function projectionPoint(x, y, a, b, c, d, e, f, g, h, image, channel) {
155
134
  * });
156
135
  */
157
136
 
158
-
159
137
  function warpingFourPoints(pts, options = {}) {
160
138
  let {
161
139
  calculateRatio = true
162
140
  } = options;
163
-
164
141
  if (pts.length !== 4) {
165
142
  throw new Error(`The array pts must have four elements, which are the four corners. Currently, pts have ${pts.length} elements`);
166
143
  }
167
-
168
144
  let [pt1, pt2, pt3, pt4] = pts;
169
145
  let quadrilaterial = [pt1, pt2, pt3, pt4];
170
146
  let [tl, tr, br, bl] = order4Points(quadrilaterial);
171
147
  let widthRect;
172
148
  let heightRect;
173
-
174
149
  if (calculateRatio) {
175
150
  [widthRect, heightRect] = computeWidthAndHeigth(tl, tr, br, bl, this.width, this.height);
176
151
  } else {
177
152
  widthRect = Math.ceil(Math.max(distance2Points(tl, tr), distance2Points(bl, br)));
178
153
  heightRect = Math.ceil(Math.max(distance2Points(tl, bl), distance2Points(tr, br)));
179
154
  }
180
-
181
155
  let newImage = _Image.default.createFrom(this, {
182
156
  width: widthRect,
183
157
  height: heightRect
184
158
  });
185
-
186
159
  let [X1, Y1] = tl;
187
160
  let [X2, Y2] = tr;
188
161
  let [X3, Y3] = br;
@@ -192,26 +165,20 @@ function warpingFourPoints(pts, options = {}) {
192
165
  let [x3, y3] = [heightRect - 1, widthRect - 1];
193
166
  let [x4, y4] = [heightRect - 1, 0];
194
167
  let S = new _mlMatrix.Matrix([[x1, y1, 1, 0, 0, 0, -x1 * X1, -y1 * X1], [x2, y2, 1, 0, 0, 0, -x2 * X2, -y2 * X2], [x3, y3, 1, 0, 0, 0, -x3 * X3, -y1 * X3], [x4, y4, 1, 0, 0, 0, -x4 * X4, -y4 * X4], [0, 0, 0, x1, y1, 1, -x1 * Y1, -y1 * Y1], [0, 0, 0, x2, y2, 1, -x2 * Y2, -y2 * Y2], [0, 0, 0, x3, y3, 1, -x3 * Y3, -y3 * Y3], [0, 0, 0, x4, y4, 1, -x4 * Y4, -y4 * Y4]]);
195
-
196
168
  let D = _mlMatrix.Matrix.columnVector([X1, X2, X3, X4, Y1, Y2, Y3, Y4]);
197
-
198
169
  let svd = new _mlMatrix.SingularValueDecomposition(S);
199
170
  let T = svd.solve(D); // solve S*T = D
200
-
201
171
  let [a, b, c, d, e, f, g, h] = T.to1DArray();
202
172
  let Xt = new _mlMatrix.Matrix(heightRect, widthRect);
203
-
204
173
  for (let channel = 0; channel < this.channels; channel++) {
205
174
  for (let i = 0; i < heightRect; i++) {
206
175
  for (let j = 0; j < widthRect; j++) {
207
176
  Xt.set(i, j, projectionPoint(i, j, a, b, c, d, e, f, g, h, this, channel));
208
177
  }
209
178
  }
210
-
211
179
  newImage.setMatrix(Xt, {
212
180
  channel: channel
213
181
  });
214
182
  }
215
-
216
183
  return newImage;
217
184
  }
@@ -4,13 +4,9 @@ Object.defineProperty(exports, "__esModule", {
4
4
  value: true
5
5
  });
6
6
  exports.default = combineChannels;
7
-
8
7
  var _Image = _interopRequireDefault(require("../Image"));
9
-
10
8
  var _model = require("../model/model");
11
-
12
9
  function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
13
-
14
10
  /**
15
11
  * Create a new grey Image by combining the channels of the current image.
16
12
  * @memberof Image
@@ -31,33 +27,26 @@ function combineChannels(method = defaultCombineMethod, options = {}) {
31
27
  this.checkProcessable('combineChannels', {
32
28
  bitDepth: [8, 16]
33
29
  });
34
-
35
30
  let newImage = _Image.default.createFrom(this, {
36
31
  components: 1,
37
32
  alpha: keepAlpha,
38
33
  colorModel: _model.GREY
39
34
  });
40
-
41
35
  let ptr = 0;
42
-
43
36
  for (let i = 0; i < this.size; i++) {
44
37
  // TODO quite slow because we create a new pixel each time
45
38
  let value = method(this.getPixel(i));
46
-
47
39
  if (mergeAlpha) {
48
40
  newImage.data[ptr++] = value * this.data[i * this.channels + this.components] / this.maxValue;
49
41
  } else {
50
42
  newImage.data[ptr++] = value;
51
-
52
43
  if (keepAlpha) {
53
44
  newImage.data[ptr++] = this.data[i * this.channels + this.components];
54
45
  }
55
46
  }
56
47
  }
57
-
58
48
  return newImage;
59
49
  }
60
-
61
50
  function defaultCombineMethod(pixel) {
62
51
  return (pixel[0] + pixel[1] + pixel[2]) / 3;
63
52
  }