Compare commits
2 Commits
1138b6216e
...
3ba1baf793
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
3ba1baf793 | ||
|
|
7875045f7a |
@ -1 +1,3 @@
|
|||||||
# this repository has been moved to [puffinsoft/jscanify](https://github.com/puffinsoft/jscanify)
|
## The repository has been moved to [puffinsoft/jscanify](https://github.com/puffinsoft/jscanify)
|
||||||
|
|
||||||
|
This is a mirror of [puffinsoft/jscanify](https://github.com/puffinsoft/jscanify). Please direct all issues, stars and forks towards that repository.
|
||||||
|
|||||||
BIN
docs/images/galaxy.png
Normal file
|
After Width: | Height: | Size: 1.2 MiB |
|
Before Width: | Height: | Size: 7.0 KiB |
|
Before Width: | Height: | Size: 3.6 MiB |
|
Before Width: | Height: | Size: 3.3 MiB |
|
Before Width: | Height: | Size: 18 KiB After Width: | Height: | Size: 24 KiB |
|
Before Width: | Height: | Size: 51 KiB After Width: | Height: | Size: 47 KiB |
|
Before Width: | Height: | Size: 103 KiB |
|
Before Width: | Height: | Size: 58 KiB |
|
Before Width: | Height: | Size: 2.4 MiB |
|
Before Width: | Height: | Size: 1.7 MiB |
|
Before Width: | Height: | Size: 1.9 MiB |
|
Before Width: | Height: | Size: 1.6 MiB |
|
Before Width: | Height: | Size: 1.5 MiB |
|
Before Width: | Height: | Size: 998 KiB |
|
Before Width: | Height: | Size: 2.1 MiB |
@ -9,7 +9,7 @@ body {
|
|||||||
#hero {
|
#hero {
|
||||||
width: 100%;
|
width: 100%;
|
||||||
overflow: hidden;
|
overflow: hidden;
|
||||||
background-image: url("images/galaxy.webp");
|
background-image: url("images/galaxy.png");
|
||||||
background-size: cover;
|
background-size: cover;
|
||||||
background-position: 0 -170px;
|
background-position: 0 -170px;
|
||||||
background-attachment: fixed;
|
background-attachment: fixed;
|
||||||
|
|||||||
@ -20,7 +20,7 @@
|
|||||||
|
|
||||||
<body>
|
<body>
|
||||||
<div id="hero" style="position: relative">
|
<div id="hero" style="position: relative">
|
||||||
<a href="https://github.com/puffinsoft/jscanify" aria-label="View the library on GitHub" target="_blank" style="position: absolute; top: 0; right: 0">
|
<a href="https://github.com/ColonelParrot/jscanify" aria-label="View the library on GitHub" target="_blank" style="position: absolute; top: 0; right: 0">
|
||||||
<svg width="80" height="80" viewBox="0 0 250 250"
|
<svg width="80" height="80" viewBox="0 0 250 250"
|
||||||
style="fill:white; color:#fff; position: absolute; top: 0; border: 0; right: 0;" aria-hidden="true">
|
style="fill:white; color:#fff; position: absolute; top: 0; border: 0; right: 0;" aria-hidden="true">
|
||||||
<path d="M0,0 L115,115 L130,115 L142,142 L250,250 L250,0 Z"></path>
|
<path d="M0,0 L115,115 L130,115 L142,142 L250,250 L250,0 Z"></path>
|
||||||
@ -32,11 +32,11 @@
|
|||||||
fill="black" class="octo-body"></path>
|
fill="black" class="octo-body"></path>
|
||||||
</svg>
|
</svg>
|
||||||
</a>
|
</a>
|
||||||
<img src="images/logo-full.png" alt="jscanify logo" style="height: 100px" />
|
<img src="images/logo-full-small.png" alt="jscanify logo" />
|
||||||
<h2>the javascript document scanning library.</h2>
|
<h2>Open-source pure Javascript implemented mobile document scanner.</h2>
|
||||||
<br />
|
<br />
|
||||||
<div class="view-on">
|
<div class="view-on">
|
||||||
<a class="view-on-option" href="https://github.com/puffinsoft/jscanify" target="_blank" style="margin: 10px">
|
<a class="view-on-option" href="https://github.com/ColonelParrot/jscanify" target="_blank" style="margin: 10px">
|
||||||
<svg width="16" height="16" aria-hidden="true" viewBox="0 0 16 16">
|
<svg width="16" height="16" aria-hidden="true" viewBox="0 0 16 16">
|
||||||
<path fill-rule="evenodd"
|
<path fill-rule="evenodd"
|
||||||
d="M8 0C3.58 0 0 3.58 0 8c0 3.54 2.29 6.53 5.47 7.59.4.07.55-.17.55-.38 0-.19-.01-.82-.01-1.49-2.01.37-2.53-.49-2.69-.94-.09-.23-.48-.94-.82-1.13-.28-.15-.68-.52-.01-.53.63-.01 1.08.58 1.23.82.72 1.21 1.87.87 2.33.66.07-.52.28-.87.51-1.07-1.78-.2-3.64-.89-3.64-3.95 0-.87.31-1.59.82-2.15-.08-.2-.36-1.02.08-2.12 0 0 .67-.21 2.2.82.64-.18 1.32-.27 2-.27.68 0 1.36.09 2 .27 1.53-1.04 2.2-.82 2.2-.82.44 1.1.16 1.92.08 2.12.51.56.82 1.27.82 2.15 0 3.07-1.87 3.75-3.65 3.95.29.25.54.73.54 1.48 0 1.07-.01 1.93-.01 2.2 0 .21.15.46.55.38A8.013 8.013 0 0016 8c0-4.42-3.58-8-8-8z">
|
d="M8 0C3.58 0 0 3.58 0 8c0 3.54 2.29 6.53 5.47 7.59.4.07.55-.17.55-.38 0-.19-.01-.82-.01-1.49-2.01.37-2.53-.49-2.69-.94-.09-.23-.48-.94-.82-1.13-.28-.15-.68-.52-.01-.53.63-.01 1.08.58 1.23.82.72 1.21 1.87.87 2.33.66.07-.52.28-.87.51-1.07-1.78-.2-3.64-.89-3.64-3.95 0-.87.31-1.59.82-2.15-.08-.2-.36-1.02.08-2.12 0 0 .67-.21 2.2.82.64-.18 1.32-.27 2-.27.68 0 1.36.09 2 .27 1.53-1.04 2.2-.82 2.2-.82.44 1.1.16 1.92.08 2.12.51.56.82 1.27.82 2.15 0 3.07-1.87 3.75-3.65 3.95.29.25.54.73.54 1.48 0 1.07-.01 1.93-.01 2.2 0 .21.15.46.55.38A8.013 8.013 0 0016 8c0-4.42-3.58-8-8-8z">
|
||||||
|
|||||||
@ -1,17 +1,17 @@
|
|||||||
{
|
{
|
||||||
"name": "jscanify",
|
"name": "jscanify",
|
||||||
"version": "1.3.2",
|
"version": "1.2.0",
|
||||||
"description": "Open-source Javascript mobile document scanner.",
|
"description": "Open-source Javascript mobile document scanner.",
|
||||||
"main": "src/jscanify-node.js",
|
"main": "src/jscanify-node.js",
|
||||||
"directories": {
|
"directories": {
|
||||||
"doc": "docs"
|
"doc": "docs"
|
||||||
},
|
},
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"test": "mocha --trace-uncaught"
|
"test": "mocha"
|
||||||
},
|
},
|
||||||
"repository": {
|
"repository": {
|
||||||
"type": "git",
|
"type": "git",
|
||||||
"url": "https://github.com/puffinsoft/jscanify.git"
|
"url": "https://github.com/ColonelParrot/jscanify.git"
|
||||||
},
|
},
|
||||||
"keywords": [
|
"keywords": [
|
||||||
"js",
|
"js",
|
||||||
@ -21,7 +21,7 @@
|
|||||||
"author": "ColonelParrot",
|
"author": "ColonelParrot",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"bugs": {
|
"bugs": {
|
||||||
"url": "https://github.com/puffinsoft/jscanify/issues"
|
"url": "https://github.com/ColonelParrot/jscanify/issues"
|
||||||
},
|
},
|
||||||
"homepage": "https://colonelparrot.github.io/jscanify/",
|
"homepage": "https://colonelparrot.github.io/jscanify/",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
|
|||||||
@ -1,4 +1,4 @@
|
|||||||
/*! jscanify v1.3.2 | (c) ColonelParrot and other contributors | MIT License */
|
/*! jscanify v1.2.0 | (c) ColonelParrot and other contributors | MIT License */
|
||||||
|
|
||||||
const { Canvas, createCanvas, Image, ImageData } = require("canvas");
|
const { Canvas, createCanvas, Image, ImageData } = require("canvas");
|
||||||
const { JSDOM } = require("jsdom");
|
const { JSDOM } = require("jsdom");
|
||||||
@ -44,13 +44,13 @@ class jscanify {
|
|||||||
*/
|
*/
|
||||||
findPaperContour(img) {
|
findPaperContour(img) {
|
||||||
const imgGray = new cv.Mat();
|
const imgGray = new cv.Mat();
|
||||||
cv.Canny(img, imgGray, 50, 200);
|
cv.cvtColor(img, imgGray, cv.COLOR_RGBA2GRAY);
|
||||||
|
|
||||||
const imgBlur = new cv.Mat();
|
const imgBlur = new cv.Mat();
|
||||||
cv.GaussianBlur(
|
cv.GaussianBlur(
|
||||||
imgGray,
|
imgGray,
|
||||||
imgBlur,
|
imgBlur,
|
||||||
new cv.Size(3, 3),
|
new cv.Size(5, 5),
|
||||||
0,
|
0,
|
||||||
0,
|
0,
|
||||||
cv.BORDER_DEFAULT
|
cv.BORDER_DEFAULT
|
||||||
@ -69,7 +69,6 @@ class jscanify {
|
|||||||
cv.RETR_CCOMP,
|
cv.RETR_CCOMP,
|
||||||
cv.CHAIN_APPROX_SIMPLE
|
cv.CHAIN_APPROX_SIMPLE
|
||||||
);
|
);
|
||||||
|
|
||||||
let maxArea = 0;
|
let maxArea = 0;
|
||||||
let maxContourIndex = -1;
|
let maxContourIndex = -1;
|
||||||
for (let i = 0; i < contours.size(); ++i) {
|
for (let i = 0; i < contours.size(); ++i) {
|
||||||
|
|||||||
@ -1,11 +1,11 @@
|
|||||||
/*! jscanify v1.3.2 | (c) ColonelParrot and other contributors | MIT License */
|
/*! jscanify v1.2.0 | (c) ColonelParrot and other contributors | MIT License */
|
||||||
|
|
||||||
(function (global, factory) {
|
(function (global, factory) {
|
||||||
typeof exports === "object" && typeof module !== "undefined"
|
typeof exports === "object" && typeof module !== "undefined"
|
||||||
? (module.exports = factory())
|
? (module.exports = factory())
|
||||||
: typeof define === "function" && define.amd
|
: typeof define === "function" && define.amd
|
||||||
? define(factory)
|
? define(factory)
|
||||||
: (global.jscanify = factory());
|
: (global.jscanify = factory());
|
||||||
})(this, function () {
|
})(this, function () {
|
||||||
"use strict";
|
"use strict";
|
||||||
|
|
||||||
@ -20,7 +20,7 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
class jscanify {
|
class jscanify {
|
||||||
constructor() { }
|
constructor() {}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Finds the contour of the paper within the image
|
* Finds the contour of the paper within the image
|
||||||
@ -29,13 +29,13 @@
|
|||||||
*/
|
*/
|
||||||
findPaperContour(img) {
|
findPaperContour(img) {
|
||||||
const imgGray = new cv.Mat();
|
const imgGray = new cv.Mat();
|
||||||
cv.Canny(img, imgGray, 50, 200);
|
cv.cvtColor(img, imgGray, cv.COLOR_RGBA2GRAY);
|
||||||
|
|
||||||
const imgBlur = new cv.Mat();
|
const imgBlur = new cv.Mat();
|
||||||
cv.GaussianBlur(
|
cv.GaussianBlur(
|
||||||
imgGray,
|
imgGray,
|
||||||
imgBlur,
|
imgBlur,
|
||||||
new cv.Size(3, 3),
|
new cv.Size(5, 5),
|
||||||
0,
|
0,
|
||||||
0,
|
0,
|
||||||
cv.BORDER_DEFAULT
|
cv.BORDER_DEFAULT
|
||||||
@ -47,7 +47,7 @@
|
|||||||
imgThresh,
|
imgThresh,
|
||||||
0,
|
0,
|
||||||
255,
|
255,
|
||||||
cv.THRESH_OTSU
|
cv.THRESH_BINARY + cv.THRESH_OTSU
|
||||||
);
|
);
|
||||||
|
|
||||||
let contours = new cv.MatVector();
|
let contours = new cv.MatVector();
|
||||||
@ -60,7 +60,6 @@
|
|||||||
cv.RETR_CCOMP,
|
cv.RETR_CCOMP,
|
||||||
cv.CHAIN_APPROX_SIMPLE
|
cv.CHAIN_APPROX_SIMPLE
|
||||||
);
|
);
|
||||||
|
|
||||||
let maxArea = 0;
|
let maxArea = 0;
|
||||||
let maxContourIndex = -1;
|
let maxContourIndex = -1;
|
||||||
for (let i = 0; i < contours.size(); ++i) {
|
for (let i = 0; i < contours.size(); ++i) {
|
||||||
|
|||||||
@ -6,75 +6,71 @@ console.log("RUNNING JSCANIFY TESTS");
|
|||||||
console.log("Warning: This may take a bit");
|
console.log("Warning: This may take a bit");
|
||||||
|
|
||||||
const { loadImage, createCanvas } = require("canvas");
|
const { loadImage, createCanvas } = require("canvas");
|
||||||
const { mkdirSync, writeFileSync, unlinkSync, existsSync, readdirSync } = require("fs");
|
const { mkdirSync, writeFileSync, unlinkSync, existsSync } = require("fs");
|
||||||
const assert = require("assert");
|
const assert = require("assert");
|
||||||
|
|
||||||
const jscanify = require("../src/jscanify-node");
|
const jscanify = require("../src/jscanify-node");
|
||||||
const path = require("path");
|
const path = require("path");
|
||||||
|
|
||||||
|
const outputPaths = {
|
||||||
|
highlight: __dirname + "/output/highlighted.jpg",
|
||||||
|
extracted: __dirname + "/output/extracted.jpg",
|
||||||
|
cornerPoints: __dirname + "/output/corner_points.jpg",
|
||||||
|
};
|
||||||
|
|
||||||
const OUTPUT_FOLDER = __dirname.replaceAll("\\", "/") + "/output/";
|
const baseFolder = __dirname.replaceAll("\\", "/") + "/output/";
|
||||||
|
|
||||||
const TEST_IMAGE_DIRECTORY = path.join(
|
const TEST_IMAGE_PATH = path.join(
|
||||||
__dirname,
|
__dirname,
|
||||||
"..",
|
"..",
|
||||||
"docs",
|
"docs",
|
||||||
"images",
|
"images",
|
||||||
"test"
|
"test",
|
||||||
|
"test.png"
|
||||||
);
|
);
|
||||||
|
|
||||||
/**
|
|
||||||
* delete previously generated output images
|
|
||||||
*/
|
|
||||||
function setup() {
|
function setup() {
|
||||||
console.log("=== setting up tests ===");
|
console.log("=== setting up tests ===");
|
||||||
console.log("Deleting previously generated images");
|
console.log("Deleting previously generated images");
|
||||||
|
Object.values(outputPaths).forEach((path) => {
|
||||||
|
if (existsSync(path)) {
|
||||||
|
unlinkSync(path);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
if (!existsSync(OUTPUT_FOLDER)) {
|
if (!existsSync(baseFolder)) {
|
||||||
mkdirSync(OUTPUT_FOLDER);
|
mkdirSync(baseFolder);
|
||||||
}
|
}
|
||||||
|
|
||||||
readdirSync(OUTPUT_FOLDER).forEach((file) => {
|
|
||||||
unlinkSync(path.join(OUTPUT_FOLDER, file));
|
|
||||||
})
|
|
||||||
}
|
}
|
||||||
|
|
||||||
console.log("=== beginning tests ===");
|
function test() {
|
||||||
console.log("loading OpenCV.js...");
|
const scanner = new jscanify();
|
||||||
|
|
||||||
const scanner = new jscanify();
|
console.log("=== beginning tests ===");
|
||||||
scanner.loadOpenCV(function (cv) {
|
console.log("loading OpenCV.js...");
|
||||||
|
scanner.loadOpenCV(function (cv) {
|
||||||
console.log("Finished loading OpenCV.js");
|
console.log("Finished loading OpenCV.js");
|
||||||
console.log("Writing test images to: " + OUTPUT_FOLDER);
|
console.log("Writing test images to: " + baseFolder);
|
||||||
|
describe("feature tests", function () {
|
||||||
/**
|
|
||||||
* tests an individual image
|
|
||||||
*/
|
|
||||||
function test(testImage, imageCount) {
|
|
||||||
describe("image #" + imageCount, function () {
|
|
||||||
it("should highlight paper", function (done) {
|
it("should highlight paper", function (done) {
|
||||||
const highlighted = scanner.highlightPaper(testImage);
|
const highlighted = scanner.highlightPaper(testImage);
|
||||||
const higlightedOutputPath = OUTPUT_FOLDER + "highlighted-" + imageCount + ".jpg";
|
|
||||||
writeFileSync(
|
writeFileSync(
|
||||||
higlightedOutputPath,
|
outputPaths.highlight,
|
||||||
highlighted.toBuffer("image/jpeg")
|
highlighted.toBuffer("image/jpeg")
|
||||||
);
|
);
|
||||||
|
|
||||||
assert.ok(existsSync(higlightedOutputPath));
|
assert.ok(existsSync(outputPaths.highlight));
|
||||||
done();
|
done();
|
||||||
});
|
});
|
||||||
|
|
||||||
it("should extract paper", function (done) {
|
it("should extract paper", function (done) {
|
||||||
const extracted = scanner.extractPaper(testImage, 386, 500);
|
const extracted = scanner.extractPaper(testImage, 386, 500);
|
||||||
const extractedOutputPath = OUTPUT_FOLDER + "extracted-" + imageCount + ".jpg";
|
|
||||||
|
|
||||||
writeFileSync(
|
writeFileSync(
|
||||||
extractedOutputPath,
|
outputPaths.extracted,
|
||||||
extracted.toBuffer("image/jpeg")
|
extracted.toBuffer("image/jpeg")
|
||||||
);
|
);
|
||||||
|
|
||||||
assert.ok(existsSync(extractedOutputPath));
|
assert.ok(existsSync(outputPaths.extracted));
|
||||||
done();
|
done();
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -107,31 +103,18 @@ scanner.loadOpenCV(function (cv) {
|
|||||||
ctx.fill();
|
ctx.fill();
|
||||||
});
|
});
|
||||||
|
|
||||||
const cornerPointsOutputPath = OUTPUT_FOLDER + "corner_points-" + imageCount + ".jpg";
|
writeFileSync(outputPaths.cornerPoints, canvas.toBuffer("image/jpeg"));
|
||||||
writeFileSync(cornerPointsOutputPath, canvas.toBuffer("image/jpeg"));
|
|
||||||
|
|
||||||
assert.ok(existsSync(cornerPointsOutputPath));
|
assert.ok(existsSync(outputPaths.cornerPoints));
|
||||||
done();
|
done();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
}
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
let testImage;
|
||||||
|
loadImage(TEST_IMAGE_PATH).then(function (image) {
|
||||||
|
testImage = image;
|
||||||
setup();
|
setup();
|
||||||
|
test();
|
||||||
let imageCount = 1;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* go through all images in test image directory
|
|
||||||
*/
|
|
||||||
readdirSync(TEST_IMAGE_DIRECTORY).forEach((file) => {
|
|
||||||
const TEST_IMAGE_PATH = path.join(TEST_IMAGE_DIRECTORY, file);
|
|
||||||
|
|
||||||
if(!file.endsWith("-sized.png")){ // these images are for the website, not testing
|
|
||||||
let tempCount = imageCount++;
|
|
||||||
|
|
||||||
loadImage(TEST_IMAGE_PATH).then(function (image) {
|
|
||||||
test(image, tempCount);
|
|
||||||
});
|
|
||||||
}
|
|
||||||
})
|
|
||||||
});
|
});
|
||||||