window.URL.createObjectURL
https://html5.xgqfrms.xyz/Canvas/safety-canvas.html

var video = document.querySelector('video');
var audio = document.querySelector('audio');
var canvas = document.querySelectorAll('canvas')[0];
var canvasForDiff = document.querySelectorAll('canvas')[1];
// video捕獲攝像頭畫面
navigator.webkitGetUserMedia({
video: true
}, success, error);
function success(stream) {
video.src = window.URL.createObjectURL(stream);
video.play();
}
function error(err) {
alert('video error: ' + err)
}
//canvas
var context = canvas.getContext('2d'),
diffCtx = canvasForDiff.getContext('2d');
//將第二個畫布混合模式設為“差異”
diffCtx.globalCompositeOperation = 'difference';
var preFrame, //前一幀
curFrame; //當前幀
var diffFrame; //存放差異幀的imageData
//捕獲並保存幀內容
function captureAndSaveFrame(){
preFrame = curFrame;
context.drawImage(video, 0, 0, 640, 480);
curFrame = canvas.toDataURL(); //轉為base64並保存
}
//繪制base64圖像到畫布上
function drawImg(src, ctx){
ctx = ctx || diffCtx;
var img = new Image();
img.src = src;
ctx.drawImage(img, 0, 0, 640, 480);
}
//渲染前后兩幀差異
function renderDiff(){
diffCtx.clearRect(0, 0, 640, 480);
drawImg(preFrame);
drawImg(curFrame);
diffFrame = diffCtx.getImageData( 0, 0, 640, 480 ); //捕獲差異幀的imageData對象
}
//計算差異
function calcDiff(){
if(!diffFrame) return 0;
var cache = arguments.callee,
count = 0;
cache.total = cache.total || 0; //整個畫布都是白色時所有像素的值的總和
for (var i = 0, l = diffFrame.width * diffFrame.height * 4; i < l; i += 4) {
count += diffFrame.data[i] + diffFrame.data[i + 1] + diffFrame.data[i + 2];
if(!cache.isLoopEver){ //只需在第一次循環里執行
cache.total += 255 * 3; //單個白色像素值
}
}
cache.isLoopEver = true;
count *= 3; //亮度放大
//返回“差異畫布高亮部分像素總值”占“畫布全亮情況像素總值”的比例
return Number(count/cache.total).toFixed(2);
}
//播放音頻
function fireAlarm(){
audio.play()
}
//定時捕獲
function timer(delta){
setTimeout(function(){
captureAndSaveFrame();
if(preFrame && curFrame){
renderDiff();
if(calcDiff() > 0.2){ //監控到異常
//發日記
submit();
//播放音頻告警
fireAlarm();
}
}
timer(delta)
}, delta || 500);
}
setTimeout(timer, 60000 * 10); //設定打開頁面十分鍾后才開始監控
//異常圖片上傳處理
function submit(){
var cache = arguments.callee,
now = Date.now();
if(cache.reqTime && (now - cache.reqTime < 5000)) return; //日記創建最小間隔為5秒
cache.reqTime = now;
//ajax 提交form
$.ajax({
url : 'http://i.cnblogs.com/EditDiary.aspx?opt=1',
type : "POST",
timeout : 5000,
data : {
'__VIEWSTATE': '',
'__VIEWSTATEGENERATOR': '4773056F',
'Editor$Edit$txbTitle': '告警' + Date.now(),
'Editor$Edit$EditorBody': '<img src="' + curFrame + '" />',
'Editor$Edit$lkbPost': '保存'
},
success: function(){
console.log('submit done')
},
error: function(err){
cache.reqTime = 0;
console.log('error: ' + err)
}
});
}
