首页 > 其他分享 >tensorflow.js 视频图片多目标检测

tensorflow.js 视频图片多目标检测

时间:2023-02-22 18:55:30浏览次数:39  
标签:box 视频 const js var tensorflow div tfjs

前言:

        Tensorflow.js 官方提供了很多常用模型库,涵盖了平时开发中大部分场景的模型。例如,前面提到的图片识别,除此之外还有人体姿态识别,目标物体识别,语音文字等识别。其中一些可能是 Python 转换而来,但都是开发人员用海量数据或资源训练的,个人觉得准确度能满足大部分功能开发要求。这里要介绍的是目标物体识别模型 ——CooSSD。

        目标检测在机器视觉中已经很常见了,就是模型可以对图片或者视频中的物体进行识别,并预测其最大概率的名称和展示概率值。以下就先以 Github 上 Coo-SSD 图片目标检测为例,最后再弄一个视频的目标实时识别。

 

demo 运行:

        tensorflow.js 提供的例子是通过 yarn,由于我本地环境原因,就以 npm 和 parcel 运行其效果。先本地创建项目文件夹,然后再分别创建 index.html, script.js, package.json 和添加几张图片。

1. 依赖包安装

(1). package.json 配置,安装 tfjs-backend-cpu, tfjs-backend-webgl 和模型

{
  "name": "tfjs-coco-ssd-demo",
  "version": "1.0.0",
  "description": "",
  "main": "index.js",
  "dependencies": {
    "@tensorflow-models/coco-ssd": "^2.2.2",
    "@tensorflow/tfjs-backend-cpu": "^3.3.0",
    "@tensorflow/tfjs-backend-webgl": "^3.3.0",
    "@tensorflow/tfjs-converter": "^3.3.0",
    "@tensorflow/tfjs-core": "^3.3.0",
    "stats.js": "^0.17.0"
  },
  "scripts": {
    "test": "echo \"Error: no test specified\" && exit 1"
  },
  "author": "",
  "license": "ISC",
  "browserslist": [
    "last 1 Chrome version"
  ]
}

(2). 命令切换到项目目录,运行 npm install

2. 代码:

(1). index.html

<h1>TensorFlow.js Object Detection</h1>
<select id='base_model'>
	<option value="lite_mobilenet_v2">SSD Lite Mobilenet V2</option>
	<option value="mobilenet_v1">SSD Mobilenet v1</option>
	<option value="mobilenet_v2">SSD Mobilenet v2</option>
</select>
<button type="button" id="run">Run</button>
<button type="button" id="toggle">Toggle Image</button>
<div>
<img id="image" />
<canvas id="canvas" width="600" height="399"></canvas>
</div>

<script src="script.js"></script>

(2). script.js

import '@tensorflow/tfjs-backend-cpu';
import '@tensorflow/tfjs-backend-webgl';

import * as cocoSsd from '@tensorflow-models/coco-ssd';

import imageURL from './image3.jpg';
import image2URL from './image5.jpg';

let modelPromise;

window.onload = () => modelPromise = cocoSsd.load();

const button = document.getElementById('toggle');
button.onclick = () => {
  image.src = image.src.endsWith(imageURL) ? image2URL : imageURL;
};

const select = document.getElementById('base_model');
select.onchange = async (event) => {
  const model = await modelPromise;
  model.dispose();
  modelPromise = cocoSsd.load(
      {base: event.srcElement.options[event.srcElement.selectedIndex].value});
};

const image = document.getElementById('image');
image.src = imageURL;

const runButton = document.getElementById('run');
runButton.onclick = async () => {
  const model = await modelPromise;
  console.log('model loaded');
  console.time('predict1');
  const result = await model.detect(image);
  console.timeEnd('predict1');


  const c = document.getElementById('canvas');
  const context = c.getContext('2d');
  context.drawImage(image, 0, 0);
  context.font = '10px Arial';

  console.log(result);

  console.log('number of detections: ', result.length);
  for (let i = 0; i < result.length; i++) {
    context.beginPath();
    context.rect(...result[i].bbox);
    context.lineWidth = 1;
    context.strokeStyle = 'green';
    context.fillStyle = 'green';
    context.stroke();
    context.fillText(
        result[i].score.toFixed(3) + ' ' + result[i].class, result[i].bbox[0],
        result[i].bbox[1] > 10 ? result[i].bbox[1] - 5 : 10);
  }
};

(3). 切换到项目目录,运行 parcel index.html

3. 运行效果

 

检测视频目标:

        经过上面 demo 的图片检测发现,用于对某资源 (图片,视频) 进行检测的函数是 detect ()。查看该函数所处 Coco-SSD 文件发现,detect 函数接收三个参数,第一个参数可以是 tensorflow 张量,也可以分别是 DOM 里的图片,视频,画布等 HTML 元素,第二第三个参数分别用于过滤返回结果的最大识别目标数和最小概率目标,而返回自然就是一个 box, 按概率值降序排列。

1. 实现流程:

(1).  给视频标签添加播放监听

(2).  页面渲染完成加载 Coco-SSD 模型

(3).  模型加载成功轮询识别视频 (video 标签)

(4).  监听到视频播放停止关闭轮询检测

2. 编码:

(1). html 部分

<style>
    #big-box {
        position: relative;
    }

    #img-box {
        position: absolute;
        top: 0px;
        left: 0px;
    }

    #img-box div {
        position: absolute;
        /*border: 2px solid #f00;*/
        pointer-events: none;
    }

    #img-box div .className {
        position: absolute;
        top: 0;
        /* background: #f00; */
        color: #fff;
    }

    #myPlayer {
        max-width: 600px;
        width: 100%;
    }
</style>

<div id="showBox">等待模型加载...</div>
<br>

<div id="big-box">
    <video id="myPlayer" muted="true" autoplay src="persons.mp4" controls="" playsinline="" webkit-playsinline=""></video>

    <div id="img-box"></div>
</div>
<script src="persons.js"></script>

(2). js 部分

import '@tensorflow/tfjs-backend-cpu';
import '@tensorflow/tfjs-backend-webgl';

import * as cocoSsd from '@tensorflow-models/coco-ssd';

var myModel = null;
var V = null;

var requestAnimationFrameIndex = null;
var myPlayer = document.getElementById("myPlayer");

var videoHeight = 0;
var videoWidth = 0;
var clientHeight = 0;
var clientWidth = 0;

var modelLoad = false;
var videoLoad = false;

window.onload = function () {

    myPlayer.addEventListener("canplay", function () {
        videoHeight = myPlayer.videoHeight;
        videoWidth = myPlayer.videoWidth;
        clientHeight = myPlayer.clientHeight;
        clientWidth = myPlayer.clientWidth;
        V = this;
        videoLoad = true;
    })

    loadModel();
}

function loadModel() {
    if (modelLoad) {
        return;
    }
    
    cocoSsd.load().then(model => {
        var showBox = document.getElementById("showBox");
        showBox.innerHTML = "载入成功";
        myModel = model;
        detectImage();
        modelLoad = true;
    });
}

function detectImage() {
    var showBox = document.getElementById("showBox");
    // 分类名
    var classList = [];
    // 分类颜色框
    var classColorMap = ["red", "green", "blue", "white"];
    // 颜色角标
    var colorCursor = 0;

    showBox.innerHTML = "检测中...";

    if (videoLoad) {
        myModel.detect(V).then(predictions => {

            showBox.innerHTML = "检测结束";

            const $imgbox = document.getElementById('img-box');

            $imgbox.innerHTML = ""

            predictions.forEach(box => {

            	if (classList.indexOf(box.class) != -1) {
            		classList.push(box.class);
            	}

            	console.log(box);

            	var borderColor = classColorMap[colorCursor%4];
// console.log(colorCursor);
// console.log(borderColor);

                const $div = document.createElement('div')
                //$div.className = 'rect';
                $div.style.border = "2px solid "+borderColor;
                var heightScale = (clientHeight / videoHeight);
                var widthScale = (clientWidth / videoWidth)
                var transformTop = box.bbox[1] * heightScale;
                var transformLeft = box.bbox[0] * widthScale;
                var transformWidth = box.bbox[2] * widthScale;
                var transformHeight = box.bbox[3] * heightScale;
                var score = box.score.toFixed(3);
                $div.style.top = transformTop + 'px'
                $div.style.left = transformLeft + 'px'
                $div.style.width = transformWidth + 'px'
                $div.style.height = transformHeight + 'px'
                $div.innerHTML = `<span class='className'>${box.class} ${score}</span>`

                $imgbox.appendChild($div)

                colorCursor++;
            })

            setTimeout(function () {
                detectImage();
            }, 10);

        });

    }
}

3. 演示效果

 

标签:box,视频,const,js,var,tensorflow,div,tfjs
From: https://www.cnblogs.com/zerofc/p/17145505.html

相关文章

  • C# json数组排序-根据指定key排序-jsonArray
    //jsonArray.ToJson()是json数组根据指定treatment_no来进行排序json字符串[{"treatment_type":"1","treatment_no":"42",},{"treatment_type":......
  • js: ElementUI表单验证validate和validateField
    文档回顾1、validate:对整个表单进行校验的方法,参数为一个回调函数。该回调函数会在校验结束后被调用,并传入两个参数:是否校验成功和未通过校验的字段。若不传入回调函数,则......
  • Qt 性能优化之二:绘制视频方案选择
    一、不太推荐使用QPainter绘制视频在Qidget上显示视频,一般是通过paintEvent,由于QPainter不是用来渲染视频的,是用来自绘GUI的,用的是CPU渲染,而不是GPU,缺乏显卡......
  • tensorflow2.0+TF-lite 各种报错
    generic_type:type"InterpreterWrapper"isalreadyregistered!原因:tensorflow2.5.0rc0版本太高,降低版本:pipinstalltensorflow==2.3  ValueErron:"batch_si......
  • 大势前瞻!文旅还是短视频,你弯道超车风口在这了
    三年前,新冠疫情的影响波及整个各行各业行业,互联网寒冬,房地产崩盘,教培团灭,在这样的背景下,行业都进入了发展“冰雪期”。老话说大疫后必有大变,如今风雪融化,万物复苏,疫情迎来......
  • js中的函数的各种形态 230222
    标准函数functionfn(){console.log(1111)}fn()匿名函数等号右边是匿名函数varfn=function(){console.log(222)}fn()自启动函数本质还是匿名函数(function()......
  • 2023年02月16日vue.js 教程
    1.创建第一个vuevue应用结构可以分成两个部分,一个是视图,一个是脚本;脚本有两个参数:el和data视图 <divid="app"> {{message}}{{name}} </div> 脚本 <......
  • E007Web学习笔记-JavaScript(五):JS事件
    一、概述1、事件概念某些组件被执行了某些操作后,触发某些代码的执行;事件:某些操作,如点击,双击,鼠标移动,键盘按下……; 2、事件源组件,如按钮、文......
  • E004Web学习笔记-JavaScript(二):JS对象
    一、Function1、概述是一个函数对象; 2、Function:函数(方法)对象①创建//1、方法1(不建议使用)varfun=newFunction(形参列表,方法体);示......
  • sqlserver、mysql、sqlite json类型数据查询及索引优化
     sqlserver:#querySELECTSalesOrderNumber,OrderDate,JSON_VALUE(Info,'$.Customer.Name')ASCustomerNameFROMSales.SalesOrderHeaderWHEREJSON_VA......