Huge News!Announcing our $40M Series B led by Abstract Ventures.Learn More
Socket
Sign inDemoInstall
Socket

@udarrr/template-matcher

Package Overview
Dependencies
Maintainers
1
Versions
65
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

@udarrr/template-matcher - npm Package Compare versions

Comparing version 1.1.7 to 1.1.8

dist/test.d.ts

7

dist/lib/image-processor.class.d.ts
import * as cv from "opencv4nodejs-prebuilt";
import { Image, Region } from "@nut-tree/nut-js";
export declare function determineROI(img: Image, roi: Region): cv.Rect;
export declare function determineMatRectROI(img: Image, roi: Region): cv.Rect;
export declare function determineRegionRectROI(roi: cv.Rect): Region;
export declare function validateSearchRegion(search: Region, screen: Region): void;

@@ -14,3 +15,3 @@ /**

*/
export declare const fromImageWithAlphaChannel: (img: Image, roi?: Region | undefined) => Promise<cv.Mat>;
export declare const fromImageWithAlphaChannel: (img: Image, roi?: cv.Rect | undefined) => Promise<cv.Mat>;
/**

@@ -25,3 +26,3 @@ * fromImageWithoutAlphaChannel should provide a way to create a library specific

*/
export declare const fromImageWithoutAlphaChannel: (img: Image, roi?: Region | undefined) => Promise<cv.Mat>;
export declare const fromImageWithoutAlphaChannel: (img: Image, roi?: cv.Rect | undefined) => Promise<cv.Mat>;
//# sourceMappingURL=image-processor.class.d.ts.map

@@ -22,9 +22,13 @@ "use strict";

Object.defineProperty(exports, "__esModule", { value: true });
exports.fromImageWithoutAlphaChannel = exports.fromImageWithAlphaChannel = exports.validateSearchRegion = exports.determineROI = void 0;
exports.fromImageWithoutAlphaChannel = exports.fromImageWithAlphaChannel = exports.validateSearchRegion = exports.determineRegionRectROI = exports.determineMatRectROI = void 0;
const cv = __importStar(require("opencv4nodejs-prebuilt"));
const nut_js_1 = require("@nut-tree/nut-js");
function determineROI(img, roi) {
function determineMatRectROI(img, roi) {
return new cv.Rect(Math.min(Math.max(roi.left, 0), img.width), Math.min(Math.max(roi.top, 0), img.height), Math.min(roi.width, img.width - roi.left), Math.min(roi.height, img.height - roi.top));
}
exports.determineROI = determineROI;
exports.determineMatRectROI = determineMatRectROI;
function determineRegionRectROI(roi) {
return new nut_js_1.Region(roi.x, roi.y, roi.width, roi.height);
}
exports.determineRegionRectROI = determineRegionRectROI;
function validateSearchRegion(search, screen) {

@@ -70,3 +74,3 @@ if (search.left < 0 ||

if (roi) {
return mat.getRegion(determineROI(img, roi));
return mat.getRegion(roi);
}

@@ -96,3 +100,3 @@ else {

if (roi) {
return mat.getRegion(determineROI(img, roi));
return mat.getRegion(roi);
}

@@ -99,0 +103,0 @@ else {

@@ -48,3 +48,3 @@ "use strict";

// WHEN
const mat = await (0, image_processor_class_1.fromImageWithoutAlphaChannel)(image, new nut_js_1.Region(-100, -100, 10, 10));
const mat = await (0, image_processor_class_1.fromImageWithoutAlphaChannel)(image, (0, image_processor_class_1.determineMatRectROI)(image, new nut_js_1.Region(-100, -100, 10, 10)));
// THEN

@@ -63,3 +63,3 @@ expect(image.hasAlphaChannel).toBeFalsy();

// WHEN
const mat = await (0, image_processor_class_1.fromImageWithoutAlphaChannel)(image, new nut_js_1.Region(10, 10, image.width * 2, image.height * 2));
const mat = await (0, image_processor_class_1.fromImageWithoutAlphaChannel)(image, (0, image_processor_class_1.determineMatRectROI)(image, new nut_js_1.Region(10, 10, image.width * 2, image.height * 2)));
// THEN

@@ -66,0 +66,0 @@ expect(image.hasAlphaChannel).toBeFalsy();

@@ -1,7 +0,5 @@

import * as cv from 'opencv4nodejs-prebuilt';
import { Image, ImageReader } from '@nut-tree/nut-js';
export default class implements ImageReader {
load(path: string): Promise<Image>;
readToMat(path: string): Promise<cv.Mat>;
}
//# sourceMappingURL=image-reader.class.d.ts.map

@@ -36,5 +36,2 @@ "use strict";

}
async readToMat(path) {
return await cv.imreadAsync(path, cv.IMREAD_GRAYSCALE);
}
}

@@ -41,0 +38,0 @@ exports.default = default_1;

@@ -30,2 +30,4 @@ import { Image, ImageFinderInterface, MatchRequest, MatchResult, Region } from '@nut-tree/nut-js';

findMatches(matchRequest: MatchRequest | CustomMatchRequest): Promise<MatchResult[]>;
private getIncreasedRectByPixelDensity;
private getDecreasedRectByPixelDensity;
private getValidatedMatches;

@@ -32,0 +34,0 @@ findMatch(matchRequest: MatchRequest | CustomMatchRequest): Promise<MatchResult>;

"use strict";
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });

@@ -10,16 +7,10 @@ const nut_js_1 = require("@nut-tree/nut-js");

const image_processor_class_1 = require("./image-processor.class");
const image_reader_class_1 = __importDefault(require("./image-reader.class"));
class TemplateMatchingFinder {
constructor() { }
async loadNeedle(image, roi) {
async loadNeedle(image) {
if (typeof image !== 'string') {
return { data: await (0, image_processor_class_1.fromImageWithAlphaChannel)(image, roi), rect: null };
return { data: await (0, image_processor_class_1.fromImageWithAlphaChannel)(image) };
}
else {
if (!roi) {
return { data: await new image_reader_class_1.default().readToMat(image), rect: null };
}
else {
return { data: await (0, image_processor_class_1.fromImageWithAlphaChannel)(await (0, nut_js_1.imageResource)(image), roi), rect: null };
}
return { data: await (0, image_processor_class_1.fromImageWithAlphaChannel)(await (0, nut_js_1.imageResource)(image)) };
}

@@ -29,20 +20,20 @@ }

if (typeof image !== 'string' && image) {
return { data: await (0, image_processor_class_1.fromImageWithAlphaChannel)(image, roi), rect: null, pixelDensity: image.pixelDensity };
let validRoi = roi ? (0, image_processor_class_1.determineMatRectROI)(image, this.getIncreasedRectByPixelDensity(roi, image.pixelDensity)) : undefined;
return { data: await (0, image_processor_class_1.fromImageWithAlphaChannel)(image, validRoi), rect: validRoi ? (0, image_processor_class_1.determineRegionRectROI)(validRoi) : undefined, pixelDensity: image.pixelDensity };
}
else {
if (!image) {
const screenPic = await nut_js_1.screen.grab();
const mat = await (0, image_processor_class_1.fromImageWithAlphaChannel)(screenPic, roi);
return { data: mat, rect: null, pixelDensity: screenPic.pixelDensity };
const imageObj = await nut_js_1.screen.grab();
let validRoi = roi ? (0, image_processor_class_1.determineMatRectROI)(imageObj, this.getIncreasedRectByPixelDensity(roi, imageObj.pixelDensity)) : undefined;
const mat = await (0, image_processor_class_1.fromImageWithAlphaChannel)(imageObj, validRoi);
return { data: mat, rect: validRoi ? (0, image_processor_class_1.determineRegionRectROI)(validRoi) : undefined, pixelDensity: imageObj.pixelDensity };
}
else {
const screenPic = await nut_js_1.screen.grab();
let mat = await (0, image_processor_class_1.fromImageWithAlphaChannel)(screenPic, roi);
if (!roi) {
return { data: mat, rect: null, pixelDensity: screenPic.pixelDensity };
}
else {
const imageObj = await (0, nut_js_1.imageResource)(image);
return { data: await (0, image_processor_class_1.fromImageWithAlphaChannel)(imageObj, roi), rect: null, pixelDensity: imageObj.pixelDensity };
}
const imageObj = await (0, nut_js_1.imageResource)(image);
let validRoi = roi ? (0, image_processor_class_1.determineMatRectROI)(imageObj, this.getIncreasedRectByPixelDensity(roi, imageObj.pixelDensity)) : undefined;
return {
data: await (0, image_processor_class_1.fromImageWithAlphaChannel)(imageObj, validRoi),
rect: validRoi ? (0, image_processor_class_1.determineRegionRectROI)(validRoi) : undefined,
pixelDensity: imageObj.pixelDensity,
};
}

@@ -59,3 +50,3 @@ }

async initData(matchRequest) {
var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k, _l, _m, _o, _p, _q, _r, _s;
var _a, _b, _c, _d, _e, _f, _g, _h;
const customMatchRequest = matchRequest;

@@ -74,21 +65,27 @@ const confidence = customMatchRequest.customOptions && ((_a = customMatchRequest.customOptions) === null || _a === void 0 ? void 0 : _a.methodType) === match_image_function_1.MethodEnum.TM_SQDIFF && matchRequest.confidence === 0.99

const debug = ((_f = customMatchRequest.customOptions) === null || _f === void 0 ? void 0 : _f.debug) || false;
const needle = await this.loadNeedle(matchRequest.needle, (_g = customMatchRequest.customOptions) === null || _g === void 0 ? void 0 : _g.roi);
const needle = await this.loadNeedle(matchRequest.needle);
if (!needle || needle.data.empty) {
throw new Error(`Failed to load ${typeof matchRequest.needle === 'string' ? matchRequest.needle : matchRequest.needle.id}, got empty image.`);
}
const haystack = await this.loadHaystack(matchRequest.haystack, (_h = customMatchRequest.customOptions) === null || _h === void 0 ? void 0 : _h.roi);
const haystack = await this.loadHaystack(matchRequest.haystack, (_g = customMatchRequest.customOptions) === null || _g === void 0 ? void 0 : _g.roi);
if (!haystack || haystack.data.empty) {
throw new Error(`Failed to load ${matchRequest && matchRequest.haystack && typeof matchRequest.haystack === 'string' && !matchRequest.haystack ? matchRequest.haystack : matchRequest.haystack.id}, got empty image.`);
}
if ((_j = customMatchRequest.customOptions) === null || _j === void 0 ? void 0 : _j.roi) {
(0, image_processor_class_1.validateSearchRegion)(new nut_js_1.Region(Number((_k = needle.rect) === null || _k === void 0 ? void 0 : _k.x), Number((_l = needle.rect) === null || _l === void 0 ? void 0 : _l.y), Number((_m = needle.rect) === null || _m === void 0 ? void 0 : _m.width), Number((_o = needle.rect) === null || _o === void 0 ? void 0 : _o.height)), new nut_js_1.Region(Number((_p = haystack.rect) === null || _p === void 0 ? void 0 : _p.x), Number((_q = haystack.rect) === null || _q === void 0 ? void 0 : _q.y), Number((_r = haystack.rect) === null || _r === void 0 ? void 0 : _r.width), Number((_s = haystack.rect) === null || _s === void 0 ? void 0 : _s.height)));
}
if (matchRequest.searchMultipleScales) {
this.throwOnTooLargeNeedle(haystack.data, needle.data, scaleSteps[scaleSteps.length - 1]);
}
return { haystack: haystack, needle: needle, confidence: confidence, scaleSteps: scaleSteps, methodType: methodType, debug: debug, searchMultipleScales: searchMultipleScales };
return {
haystack: haystack,
needle: needle,
confidence: confidence,
scaleSteps: scaleSteps,
methodType: methodType,
debug: debug,
searchMultipleScales: searchMultipleScales,
roi: (_h = customMatchRequest.customOptions) === null || _h === void 0 ? void 0 : _h.roi,
};
}
async findMatches(matchRequest) {
let matchResults = [];
let { haystack, needle, confidence, scaleSteps, methodType, debug, searchMultipleScales } = await this.initData(matchRequest);
let { haystack, needle, confidence, scaleSteps, methodType, debug, searchMultipleScales, roi } = await this.initData(matchRequest);
if (!searchMultipleScales) {

@@ -102,18 +99,33 @@ const overwrittenResults = await match_image_function_1.MatchTemplate.matchImagesByWriteOverFounded(haystack.data, needle.data, confidence, methodType, debug);

}
return await this.getValidatedMatches(matchResults, haystack.pixelDensity, confidence);
return await this.getValidatedMatches(matchResults, haystack.pixelDensity, confidence, roi);
}
async getValidatedMatches(matchResults, pixelDensity, confidence) {
const matches = await Promise.all(matchResults).then((results) => {
results.forEach((matchResult) => {
matchResult.location.left /= pixelDensity.scaleX && pixelDensity.scaleY && pixelDensity.scaleX === pixelDensity.scaleY ? pixelDensity.scaleX : 1;
matchResult.location.width /= pixelDensity.scaleX && pixelDensity.scaleY && pixelDensity.scaleX === pixelDensity.scaleY ? pixelDensity.scaleX : 1;
matchResult.location.top /= pixelDensity.scaleX && pixelDensity.scaleY && pixelDensity.scaleX === pixelDensity.scaleY ? pixelDensity.scaleX : 1;
matchResult.location.height /= pixelDensity.scaleX && pixelDensity.scaleY && pixelDensity.scaleX === pixelDensity.scaleY ? pixelDensity.scaleX : 1;
getIncreasedRectByPixelDensity(rect, pixelDensity) {
rect.left *= pixelDensity.scaleX && pixelDensity.scaleY && pixelDensity.scaleX === pixelDensity.scaleY ? pixelDensity.scaleX : 1;
rect.width *= pixelDensity.scaleX && pixelDensity.scaleY && pixelDensity.scaleX === pixelDensity.scaleY ? pixelDensity.scaleX : 1;
rect.top *= pixelDensity.scaleX && pixelDensity.scaleY && pixelDensity.scaleX === pixelDensity.scaleY ? pixelDensity.scaleX : 1;
rect.height *= pixelDensity.scaleX && pixelDensity.scaleY && pixelDensity.scaleX === pixelDensity.scaleY ? pixelDensity.scaleX : 1;
return rect;
}
getDecreasedRectByPixelDensity(matchResults, pixelDensity) {
return matchResults.map((results) => {
return {
confidence: results.confidence,
error: results.error,
location: new nut_js_1.Region((results.location.left /= pixelDensity.scaleX && pixelDensity.scaleY && pixelDensity.scaleX === pixelDensity.scaleY ? pixelDensity.scaleX : 1), (results.location.top /= pixelDensity.scaleX && pixelDensity.scaleY && pixelDensity.scaleX === pixelDensity.scaleY ? pixelDensity.scaleX : 1), (results.location.width /= pixelDensity.scaleX && pixelDensity.scaleY && pixelDensity.scaleX === pixelDensity.scaleY ? pixelDensity.scaleX : 1), (results.location.height /= pixelDensity.scaleX && pixelDensity.scaleY && pixelDensity.scaleX === pixelDensity.scaleY ? pixelDensity.scaleX : 1)),
};
});
}
async getValidatedMatches(matchResults, pixelDensity, confidence, roi) {
matchResults = this.getDecreasedRectByPixelDensity(matchResults, pixelDensity);
if (roi) {
matchResults = matchResults.map((m) => {
return { confidence: m.confidence, error: m.error, location: new nut_js_1.Region(m.location.left + roi.left, m.location.top + roi.top, m.location.width, m.location.height) };
});
return results.sort((first, second) => second.confidence - first.confidence);
});
const potentialMatches = matches.filter((match) => match.confidence >= confidence);
(0, image_processor_class_1.validateSearchRegion)(new nut_js_1.Region(Number(roi.left), Number(roi.top), Number(roi.width), Number(roi.height)), new nut_js_1.Region(0, 0, await nut_js_1.screen.width(), await nut_js_1.screen.height()));
}
matchResults.sort((first, second) => second.confidence - first.confidence);
const potentialMatches = matchResults.filter((match) => match.confidence >= confidence);
if (potentialMatches.length === 0) {
matches.sort((a, b) => a.confidence - b.confidence);
const bestMatch = matches.pop();
matchResults.sort((a, b) => a.confidence - b.confidence);
const bestMatch = matchResults.pop();
if (bestMatch) {

@@ -129,6 +141,6 @@ throw new Error(`No match with required confidence ${confidence}. Best match: ${bestMatch.confidence}`);

async findMatch(matchRequest) {
let { haystack, needle, confidence, scaleSteps, methodType, debug, searchMultipleScales } = await this.initData(matchRequest);
let { haystack, needle, confidence, scaleSteps, methodType, debug, searchMultipleScales, roi } = await this.initData(matchRequest);
if (!searchMultipleScales) {
const matches = await match_image_function_1.MatchTemplate.matchImages(haystack.data, needle.data, methodType, debug);
const result = await this.getValidatedMatches([matches.data], haystack.pixelDensity, confidence);
const result = await this.getValidatedMatches([matches.data], haystack.pixelDensity, confidence, roi);
return result[0];

@@ -138,3 +150,3 @@ }

const scaledResults = await this.searchMultipleScales(haystack.data, needle.data, confidence, scaleSteps, methodType, debug, true);
return (await this.getValidatedMatches([scaledResults[0]], haystack.pixelDensity, confidence))[0];
return (await this.getValidatedMatches([scaledResults[0]], haystack.pixelDensity, confidence, roi))[0];
}

@@ -141,0 +153,0 @@ }

{
"name": "@udarrr/template-matcher",
"version": "1.1.7",
"version": "1.1.8",
"main": "dist/index",

@@ -60,2 +60,3 @@ "typings": "dist/index",

"dependencies": {
"@nut-tree/nut-js": "^2.3.0",
"opencv4nodejs-prebuilt": "5.3.4"

@@ -62,0 +63,0 @@ },

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc