modify tensforflow plugin syntax

merge-requests/7/head
Moe 2018-06-19 21:13:58 -07:00
parent 766454becb
commit 0b7a094506
3 changed files with 81 additions and 289 deletions

View File

@ -1,4 +1,9 @@
#!/bin/bash
mkdir data
mkdir data/inception
chmod -R 777 data
wget https://cdn.shinobi.video/weights/inception5h.zip -O inception5h.zip
unzip inception5h.zip -d data/inception
if [ $(dpkg-query -W -f='${Status}' opencv_version 2>/dev/null | grep -c "ok installed") -eq 0 ]; then
echo "Shinobi - Do ypu want to let the `opencv4nodejs` npm package install OpenCV? "
echo "Only do this if you do not have OpenCV already or will not use a GPU (Hardware Acceleration)."

View File

@ -1,212 +0,0 @@
//
// Shinobi - OpenCV Plugin
// Copyright (C) 2016-2025 Moe Alam, moeiscool
//
// # Donate
//
// If you like what I am doing here and want me to continue please consider donating :)
// PayPal : paypal@m03.a
//
process.on('uncaughtException', function (err) {
console.error('uncaughtException',err);
});
var fs=require('fs');
var cv=require('opencv');
var exec = require('child_process').exec;
var moment = require('moment');
var config=require('./conf.json');
if(config.systemLog===undefined){config.systemLog=true}
s={
group:{},
dir:{
cascades:__dirname+'/cascades/'
},
isWin:(process.platform==='win32')
}
//default stream folder check
if(!config.streamDir){
if(s.isWin===false){
config.streamDir='/dev/shm'
}else{
config.streamDir=config.windowsTempDir
}
if(!fs.existsSync(config.streamDir)){
config.streamDir=__dirname+'/streams/'
}else{
config.streamDir+='/streams/'
}
}
s.dir.streams=config.streamDir;
//streams dir
if(!fs.existsSync(s.dir.streams)){
fs.mkdirSync(s.dir.streams);
}
s.gid=function(x){
if(!x){x=10};var t = "";var p = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789";
for( var i=0; i < x; i++ )
t += p.charAt(Math.floor(Math.random() * p.length));
return t;
};
s.systemLog=function(q,w,e){
if(!w){w=''}
if(!e){e=''}
if(config.systemLog===true){
return console.log(moment().format(),q,w,e)
}
}
s.findCascades=function(callback){
var tmp={};
tmp.foundCascades=[];
fs.readdir(s.dir.cascades,function(err,files){
files.forEach(function(cascade,n){
if(cascade.indexOf('.xml')>-1){
tmp.foundCascades.push(cascade.replace('.xml',''))
}
})
s.cascadesInDir=tmp.foundCascades;
callback(tmp.foundCascades)
})
}
s.findCascades(function(){
//get cascades
})
s.detectObject=function(buffer,d){
var keys = Object.keys(d.mon.detector_cascades);
if(d.mon.detector_lisence_plate==="1"){
if(!d.mon.detector_lisence_plate_country||d.mon.detector_lisence_plate_country===''){
d.mon.detector_lisence_plate_country='us'
}
d.tmpFile=s.gid(5)+'.jpg'
if(!fs.existsSync(s.dir.streams)){
fs.mkdirSync(s.dir.streams);
}
d.dir=s.dir.streams+d.ke+'/'
if(!fs.existsSync(d.dir)){
fs.mkdirSync(d.dir);
}
d.dir=s.dir.streams+d.ke+'/'+d.id+'/'
if(!fs.existsSync(d.dir)){
fs.mkdirSync(d.dir);
}
fs.writeFile(d.dir+d.tmpFile,buffer,function(err){
if(err) return s.systemLog(err);
exec('alpr -j -c '+d.mon.detector_lisence_plate_country+' '+d.dir+d.tmpFile,{encoding:'utf8'},(err, scan, stderr) => {
if(err){
s.systemLog(err);
}else{
try{
try{
scan=JSON.parse(scan)
}catch(err){
if(!scan||!scan.results){
return s.systemLog(scan,err);
}
}
if(scan.results.length>0){
scan.plates=[]
scan.mats=[]
scan.results.forEach(function(v){
v.candidates.forEach(function(g,n){
if(v.candidates[n].matches_template)
delete(v.candidates[n].matches_template)
})
scan.plates.push({coordinates:v.coordinates,candidates:v.candidates,confidence:v.confidence,plate:v.plate})
var width = Math.sqrt( Math.pow(v.coordinates[1].x - v.coordinates[0].x, 2) + Math.pow(v.coordinates[1].y - v.coordinates[0].y, 2));
var height = Math.sqrt( Math.pow(v.coordinates[2].x - v.coordinates[1].x, 2) + Math.pow(v.coordinates[2].y - v.coordinates[1].y, 2))
scan.mats.push({
x:v.coordinates[0].x,
y:v.coordinates[0].y,
width:width,
height:height,
tag:v.plate
})
})
tx({f:'trigger',id:d.id,ke:d.ke,details:{plug:config.plug,name:'licensePlate',reason:'object',matrices:scan.mats,confidence:d.average,imgHeight:d.mon.detector_scale_y,imgWidth:d.mon.detector_scale_x,frame:d.base64}})
}
}catch(err){
s.systemLog(err);
}
}
exec('rm -rf '+d.dir+d.tmpFile,{encoding:'utf8'})
})
})
}
if(keys.length===0){return false}
cv.readImage(buffer, function(err,im){
if(err){console.log(err);return false;}
var width = im.width();
var height = im.height();
if (width < 1 || height < 1) {
throw new Error('Image has no size');
}
keys.forEach(function(v,n){
im.detectObject(s.dir.cascades+v+'.xml',{}, function(err,mats){
if(err){console.log(err);return false;}
if(mats&&mats.length>0){
s.cx({f:'trigger',id:d.id,ke:d.ke,details:{plug:config.plug,name:v,reason:'object',matrices:mats,confidence:d.average,imgHeight:height,imgWidth:width}})
}
})
})
})
}
io = require('socket.io-client')('ws://'+config.host+':'+config.port);//connect to master
s.cx=function(x){x.pluginKey=config.key;x.plug=config.plug;return io.emit('ocv',x)}
io.on('connect',function(d){
s.cx({f:'init',plug:config.plug});
})
io.on('disconnect',function(d){
io.connect()
})
io.on('f',function(d){
switch(d.f){
case'refreshPlugins':
s.findCascades(function(cascades){
s.cx({f:'s.tx',data:{f:'detector_cascade_list',cascades:cascades},to:'GRP_'+d.ke})
})
break;
case'readPlugins':
s.cx({f:'s.tx',data:{f:'detector_cascade_list',cascades:s.cascadesInDir},to:'GRP_'+d.ke})
break;
case'init_monitor':
if(s.group[d.ke]&&s.group[d.ke][d.id]){
s.group[d.ke][d.id].canvas={}
s.group[d.ke][d.id].canvasContext={}
s.group[d.ke][d.id].blendRegion={}
s.group[d.ke][d.id].blendRegionContext={}
s.group[d.ke][d.id].lastRegionImageData={}
delete(s.group[d.ke][d.id].cords)
delete(s.group[d.ke][d.id].buffer)
}
break;
case'frame':
d.details={}
try{
if(!s.group[d.ke]){
s.group[d.ke]={}
}
if(!s.group[d.ke][d.id]){
s.group[d.ke][d.id]={
canvas:{},
canvasContext:{},
lastRegionImageData:{},
blendRegion:{},
blendRegionContext:{},
}
}
if(!s.group[d.ke][d.id].buffer){
s.group[d.ke][d.id].buffer=[d.frame];
}else{
s.group[d.ke][d.id].buffer.push(d.frame)
}
if(d.frame[d.frame.length-2] === 0xFF && d.frame[d.frame.length-1] === 0xD9){
s.group[d.ke][d.id].buffer=Buffer.concat(s.group[d.ke][d.id].buffer);
s.detectObject(s.group[d.ke][d.id].buffer,d)
s.group[d.ke][d.id].buffer=null;
}
} catch(err){
console.error(err)
}
break;
}
})

View File

@ -16,6 +16,7 @@ var exec = require('child_process').exec;
var moment = require('moment');
var Canvas = require('canvas');
var express = require('express');
const path = require('path');
var http = require('http'),
app = express(),
server = http.createServer(app);
@ -135,93 +136,91 @@ s.detectLicensePlate=function(buffer,d,tx){
})
}
s.detectObject=function(buffer,d,tx){
//detect license plate?
if(d.mon.detector_lisence_plate==="1"){
s.detectLicensePlate(buffer,d,tx)
}
cv.imdecodeAsync(buffer,(err,im) => {
if(err){
console.log(err)
return
}
const cv = require('../');
const fs = require('fs');
const path = require('path');
//detect license plate?
if(d.mon.detector_lisence_plate==="1"){
s.detectLicensePlate(buffer,d,tx)
}
cv.imdecodeAsync(buffer,(err,im) => {
if(err){
console.log(err)
return
}
if (!cv.xmodules.dnn) {
throw new Error('exiting: opencv4nodejs compiled without dnn module');
}
if (!cv.xmodules.dnn) {
throw new Error('exiting: opencv4nodejs compiled without dnn module');
}
// replace with path where you unzipped inception model
const inceptionModelPath = '__dirname/tf-inception';
// replace with path where you unzipped inception model
const inceptionModelPath = __dirname+'/data/inception';
const modelFile = path.resolve(inceptionModelPath, 'tensorflow_inception_graph.pb');
const classNamesFile = path.resolve(inceptionModelPath, 'imagenet_comp_graph_label_strings.txt');
if (!fs.existsSync(modelFile) || !fs.existsSync(classNamesFile)) {
console.log('could not find inception model');
console.log('download the model from: https://storage.googleapis.com/download.tensorflow.org/models/inception5h.zip');
throw new Error('exiting');
}
const modelFile = path.resolve(inceptionModelPath, 'tensorflow_inception_graph.pb');
const classNamesFile = path.resolve(inceptionModelPath, 'imagenet_comp_graph_label_strings.txt');
if (!fs.existsSync(modelFile) || !fs.existsSync(classNamesFile)) {
console.log('could not find inception model');
console.log('download the model from: https://cdn.shinobi.video/weights/inception5h.zip');
throw new Error('exiting');
}
// read classNames and store them in an array
const classNames = fs.readFileSync(classNamesFile).toString().split('\n');
// read classNames and store them in an array
const classNames = fs.readFileSync(classNamesFile).toString().split('\n');
// initialize tensorflow inception model from modelFile
const net = cv.readNetFromTensorflow(modelFile);
// initialize tensorflow inception model from modelFile
const net = cv.readNetFromTensorflow(modelFile);
const classifyImg = (im) => {
// inception model works with 224 x 224 images, so we resize
// our input images and pad the image with white pixels to
// make the images have the same width and height
const maxImgDim = 224;
const white = new cv.Vec(255, 255, 255);
const imgResized = img.resizeToMax(maxImgDim).padToSquare(white);
// inception model works with 224 x 224 images, so we resize
// our input images and pad the image with white pixels to
// make the images have the same width and height
const maxImgDim = 224;
const white = new cv.Vec(255, 255, 255);
const imgResized = im.resizeToMax(maxImgDim).padToSquare(white);
// network accepts blobs as input
const inputBlob = cv.blobFromImage(imgResized);
net.setInput(inputBlob);
// network accepts blobs as input
const inputBlob = cv.blobFromImage(imgResized);
net.setInput(inputBlob);
// forward pass input through entire network, will return
// classification result as 1xN Mat with confidences of each class
const outputBlob = net.forward();
// forward pass input through entire network, will return
// classification result as 1xN Mat with confidences of each class
const outputBlob = net.forward();
// find all labels with a minimum confidence
const minConfidence = 0.05;
const locations =
outputBlob
.threshold(minConfidence, 1, cv.THRESH_BINARY)
.convertTo(cv.CV_8U)
.findNonZero();
const result =
locations.map(pt => ({
confidence: parseInt(outputBlob.at(0, pt.x) * 100) / 100,
className: classNames[pt.x]
}))
// sort result by confidence
.sort((r0, r1) => r1.confidence - r0.confidence)
.map(res => `${res.className} (${res.confidence})`);
if(result.length > 0) {
s.cx({
f:'trigger',
id:d.id,
ke:d.ke,
name:cascade,
details:{
plug:'tensorflow',
name:'tensorflow',
reason:result,
matrices : matrices
// confidence:d.average
},
imgHeight:d.mon.detector_scale_y,
imgWidth:d.mon.detector_scale_x
})
}
// return result;
};
})
// find all labels with a minimum confidence
const minConfidence = 0.05;
const locations =
outputBlob
.threshold(minConfidence, 1, cv.THRESH_BINARY)
.convertTo(cv.CV_8U)
.findNonZero();
// locations.forEach(function(v){
// console.log(v)
// })
const result =
locations.map(pt => ({
confidence: parseInt(outputBlob.at(0, pt.x) * 100) / 100,
className: classNames[pt.x]
}))
// sort result by confidence
.sort((r0, r1) => r1.confidence - r0.confidence)
.map(res => `${res.className} (${res.confidence})`);
console.log(result)
if(result.length > 0) {
s.cx({
f:'trigger',
id:d.id,
ke:d.ke,
name:'tensorflow',
details:{
plug:'tensorflow',
name:'tensorflow',
reason:'object',
matrices : result
// confidence:d.average
},
imgHeight:d.mon.detector_scale_y,
imgWidth:d.mon.detector_scale_x
})
}
})
}
s.systemLog=function(q,w,e){
if(!w){w=''}
if(!e){e=''}