成人国产在线小视频_日韩寡妇人妻调教在线播放_色成人www永久在线观看_2018国产精品久久_亚洲欧美高清在线30p_亚洲少妇综合一区_黄色在线播放国产_亚洲另类技巧小说校园_国产主播xx日韩_a级毛片在线免费

資訊專欄INFORMATION COLUMN

媒體流數(shù)據(jù)獲取和人臉檢測(cè)

chadLi / 2402人閱讀

摘要:入?yún)⑹且粋€(gè)對(duì)象是判斷是否啟動(dòng)攝像頭和錄音,返回一個(gè)對(duì)象。這個(gè)包可以把你想要檢測(cè)的圖片視頻以及攝像頭上面的內(nèi)容都是支持捕捉人臉和檢測(cè)面部特征。我這里主要實(shí)現(xiàn)的是攝像頭捕捉人臉和檢測(cè)面部特征。

背景

由于最近這些年互聯(lián)網(wǎng)面向的受眾面越來(lái)越光,有了更多的人和設(shè)備訪問互聯(lián)網(wǎng),這也就意味著我們要做的就越來(lái)越多, 不在是像以前那樣只需要調(diào)整頁(yè)面樣式和切圖就可以了。所以就有了這篇文章的誕生,本次講的如何在本地喚醒相機(jī)然后進(jìn)行拍照,同時(shí)對(duì)拍照的照片進(jìn)行修改,還可以對(duì)攝像頭所捕捉的數(shù)據(jù)進(jìn)行一個(gè)轉(zhuǎn)發(fā),同時(shí)還可以檢測(cè)攝像頭中是否存在人。

關(guān)鍵字API以及兼容性

喚醒攝像頭主要用的API是 navigator.mediaDevices.getUserMedia。入?yún)⑹且粋€(gè)對(duì)象{ audio: true, video: true } 是判斷是否啟動(dòng)攝像頭和錄音,返回一個(gè)promise對(duì)象。以前的navigator.getUserMedia已經(jīng)被廢棄。如果video沒有設(shè)置自動(dòng)播放 需要在成功回調(diào)函數(shù)那里手動(dòng)調(diào)用執(zhí)行,只有這樣攝像頭才會(huì)被執(zhí)行,不然就不會(huì)正確顯示。

目前 IOS 設(shè)備的微信和 Safari 均不支持,較新的安卓和桌面端瀏覽器均支持。另外,出于安全問題考慮,Chrome 只支持 HTTPS 頁(yè)面啟用攝像頭。

開啟本地相機(jī)

test是用vue來(lái)的。因?yàn)榭紤]到到時(shí)候直接復(fù)制就好,所以在用的時(shí)候需要考慮自己的環(huán)境來(lái)進(jìn)行部分修改和調(diào)整

  HTML部分
  
  
CSS部分 #photo { border: 1px solid black; width: 320px; height: 240px; } #canvas { display: none; } .camera { width: 340px; display: inline-block; } .output { width: 340px; display: inline-block; } #startbutton { display: block; position: relative; margin-left: auto; margin-right: auto; bottom: 32px; background-color: rgba(0, 150, 0, 0.5); border: 1px solid rgba(255, 255, 255, 0.7); box-shadow: 0px 0px 1px 2px rgba(0, 0, 0, 0.2); font-size: 14px; font-family: "Lucida Grande", "Arial", sans-serif; color: rgba(255, 255, 255, 1); } .contentarea { font-size: 16px; font-family: "Lucida Grande", "Arial", sans-serif; width: 760px; } JS部分 // 監(jiān)聽攝像頭是否啟動(dòng)成功并且按照4:3的比例初始化攝像頭和畫布 canplay () { let { video, canvas } = this.$refs if (!this.streaming) { this.height = video.videoHeight / (video.videoWidth / this.width); console.log(this.height) if (isNaN(this.height)) { this.height = this.width / (4 / 3); } video.setAttribute("width", this.width); video.setAttribute("height", this.height); canvas.setAttribute("width", this.width); canvas.setAttribute("height", this.height); this.streaming = true; } }, // 獲取攝像頭被點(diǎn)擊的那一刻的數(shù)據(jù)并且存到canvas里面以便進(jìn)行修改 然后在存儲(chǔ)在img標(biāo)簽顯示在頁(yè)面 takepicture () { let { video, canvas, photo } = this.$refs let context = canvas.getContext("2d") if (this.width && this.height) { canvas.width = this.width; canvas.height = this.height; context.drawImage(video, 0, 0, this.width, this.height); let data = canvas.toDataURL("image/png"); photo.setAttribute("src", data); } else { this.clearphoto(); } }, // 清除canvas信息 clearphoto () { let { canvas, photo } = this.$refs var context = canvas.getContext("2d"); context.fillStyle = "#AAA"; context.fillRect(0, 0, canvas.width, canvas.height); var data = canvas.toDataURL("image/png"); photo.setAttribute("src", data); }, // 初始化攝像頭調(diào)用 startup() { let { video } = this.$refs this.width = 320 this.height = 0 this.streaming = false navigator.mediaDevices .getUserMedia({ video: true, audio: false }) .then((stream) => { video.srcObject = stream; video.play(); }) .catch((err) => { console.log("An error occurred: " + err); }) }

autoplay 需要開啟自動(dòng)播放不然需要在成功的回調(diào)里面手動(dòng)執(zhí)行,不然不會(huì)顯示內(nèi)容. 如果只是開啟攝像頭部分我們不需要聲音,所以關(guān)閉掉了

 
 

我們需要等頁(yè)面加載之后手動(dòng)開啟攝像頭方法。

mounted() {
   this.startup()
}

startup() {
  let { video } = this.$refs // 獲取頁(yè)面上面的視頻元素
  this.width = 320 // 初始化寬度
  this.height = 0 // 初始化高度
  this.streaming = false // 初始化是否進(jìn)行中
  navigator.mediaDevices
    .getUserMedia({ video: true, audio: false }) // 這里我們只開啟攝像頭
    .then((stream) => { // 成功的執(zhí)行
      video.srcObject = stream;
    })
    .catch((err) => { // 失敗的執(zhí)行
      console.error("An error occurred: " + err);
    })
},

當(dāng)攝像頭被成功啟動(dòng)之后, 就會(huì)執(zhí)行 canplay 方法

 canplay () {
  let { video, canvas } = this.$refs // 獲取節(jié)點(diǎn) 
  if (!this.streaming) { // 是否是在運(yùn)行中 如果是
    this.height = video.videoHeight / (video.videoWidth / this.width); // 初始化高度
    console.log(this.height)
    if (isNaN(this.height)) { // 這里初始化高度是為了和寬度進(jìn)行一個(gè)響應(yīng) 初始成一個(gè)4:3的比例
      this.height = this.width / (4 / 3);
    }
    video.setAttribute("width", this.width); // 這個(gè)時(shí)候開始設(shè)置節(jié)點(diǎn)的寬度和高度
    video.setAttribute("height", this.height);
    canvas.setAttribute("width", this.width);
    canvas.setAttribute("height", this.height);
    this.streaming = true;
  }
}

這個(gè)時(shí)候攝像頭的基本也就已經(jīng)操作完畢了 如果沒有一場(chǎng)的時(shí)候就可以在頁(yè)面上看到你攝像頭所捕捉到的內(nèi)容 這個(gè)時(shí)候我們需要把你想要捕捉的內(nèi)容轉(zhuǎn)成圖片顯示到頁(yè)面上

takepicture () { // 點(diǎn)擊方法 當(dāng)我們點(diǎn)擊 Take photo 按鈕的時(shí)候 這個(gè)時(shí)候把這部分的信息轉(zhuǎn)成圖片
  let { video, canvas, photo } = this.$refs // 獲取節(jié)點(diǎn)
  let context = canvas.getContext("2d")
  if (this.width && this.height) { // 把video的數(shù)據(jù)存入canvas以便我們進(jìn)行其他操作 轉(zhuǎn)成圖片資源然后顯示在頁(yè)面上
    canvas.width = this.width;
    canvas.height = this.height;
    context.drawImage(video, 0, 0, this.width, this.height);
    let data = canvas.toDataURL("image/png");
    photo.setAttribute("src", data);
  } else { // 如果初始化的寬高不存在 這個(gè)時(shí)候說(shuō)明有異常需要排除,同時(shí)清除掉畫布上面的圖片數(shù)據(jù)
    this.clearphoto();
  }
},
clearphoto () { // 清除畫布圖片數(shù)據(jù) 同時(shí)更新img
  let { canvas, photo } = this.$refs
  var context = canvas.getContext("2d");
  context.fillStyle = "#AAA";
  context.fillRect(0, 0, canvas.width, canvas.height);

  var data = canvas.toDataURL("image/png");
  photo.setAttribute("src", data);
},
對(duì)攝像頭捕捉的畫面進(jìn)行獲取和解析 應(yīng)用場(chǎng)景

完成以上步驟之后,沒有問題。我們就可以喚醒連接的攝像頭設(shè)備,捕捉你想要的畫面存到你想要存的地方。當(dāng)我們把捕捉到的畫面存到canvas里面去之后,我們可以進(jìn)行很多操作,可以對(duì)你捕捉的畫面增加你想要的特效,這個(gè)時(shí)候canvas能夠?qū)崿F(xiàn)的功能都可以在你捕捉到畫面上面實(shí)現(xiàn),并且轉(zhuǎn)成圖片。
此時(shí),攝像頭所捕捉到的內(nèi)容還是單向的,無(wú)法與別人通訊。如果你想實(shí)現(xiàn)一種類似于視頻聊天的功能。這個(gè)時(shí)候就要改一下我們的代碼,參考一下webRTC即時(shí)通訊協(xié)議。需要搭建一個(gè)第三方的信令服務(wù)器,來(lái)進(jìn)行雙向通訊。

人臉檢測(cè)工具的使用

我現(xiàn)在借助的是的face-api這款工具 有捕捉人臉,檢測(cè)面部特征。這個(gè)包可以把你想要檢測(cè)的圖片視頻以及攝像頭上面的內(nèi)容都是支持捕捉人臉和檢測(cè)面部特征。我這里主要實(shí)現(xiàn)的是攝像頭捕捉人臉和檢測(cè)面部特征。

官網(wǎng): https://github.com/justadudew...

HTML部分


JS部分

const video = document.getElementById("video"); // 獲取節(jié)點(diǎn)
Promise.all([ // 加載我想要使用的模型 同時(shí)對(duì)應(yīng)的josn文件和shard文件要處在同一目錄 不然讀取的時(shí)候可能讀取不到。當(dāng)你讀取不到的時(shí)候你可能會(huì)報(bào) SyntaxError: Unexpected token < in JSON at position 0。這點(diǎn)略坑
  faceapi.nets.tinyFaceDetector.loadFromUri("/models"),
  faceapi.nets.faceLandmark68Net.loadFromUri("/models"),
  faceapi.nets.faceRecognitionNet.loadFromUri("/models"),
  faceapi.nets.faceExpressionNet.loadFromUri("/models")
]).then(startVideo); // 載入成功之后喚醒攝像頭

function startVideo() {
  navigator.getUserMedia(
    { video: {} },
    stream => (video.srcObject = stream),
    err => console.error(err)
  );
}

video.addEventListener("play", () => { // 當(dāng)攝像頭成功啟動(dòng)之后 開始執(zhí)行這部分的方法
  const canvas = faceapi.createCanvasFromMedia(video); // 創(chuàng)建一個(gè)畫布
  document.body.append(canvas);
  const displaySize = { width: 640, height: 480 }; // 這部分的大小是等同video的大小的
  faceapi.matchDimensions(canvas, displaySize); // 聲明大小
  setInterval(async () => { // 我們需要持續(xù)傳遞攝像頭的數(shù)據(jù)
    const detections = await faceapi
      .detectAllFaces(video, new faceapi.TinyFaceDetectorOptions())
      .withFaceLandmarks()
      .withFaceExpressions();
    const resizedDetections = faceapi.resizeResults(
      detections,
      displaySize
    );
    canvas.getContext("2d").clearRect(0, 0, canvas.width, canvas.height);
    faceapi.draw.drawDetections(canvas, resizedDetections);
    faceapi.draw.drawFaceLandmarks(canvas, resizedDetections);
    faceapi.draw.drawFaceExpressions(canvas, resizedDetections);
  }, 100);
});
場(chǎng)景

文章版權(quán)歸作者所有,未經(jīng)允許請(qǐng)勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉(zhuǎn)載請(qǐng)注明本文地址:http://systransis.cn/yun/104917.html

相關(guān)文章

  • 【名額有限】云開發(fā)AI拓展能力等你來(lái)體驗(yàn)!

    摘要:一鍵部署后端能力首先需要開通云開發(fā)的人臉特征分析與檢測(cè)擴(kuò)展能力,并完成授權(quán)。云開發(fā)與云開發(fā)和本沒有特別大的關(guān)聯(lián),使用云開發(fā)可以化調(diào)用騰訊云的能力,然鵝來(lái)自官方的云開發(fā)擴(kuò)展能力解決方案卻讓這兩者發(fā)生了奇妙的化學(xué)反應(yīng)。 這次來(lái)了個(gè)超厲害的新能力!人臉智能打馬賽克、人臉智能裁剪……各種操作,都能一步到位!迫不及待想體驗(yàn),戳鏈接:https://wj.qq.com/s2/3986990/......

    Simon 評(píng)論0 收藏0
  • 阿里巴巴直播內(nèi)容風(fēng)險(xiǎn)防控中的AI力量

    摘要:阿里巴巴集團(tuán)安全部今年在直播管控中的特色在于大量采用人工智能和深度學(xué)習(xí)等技術(shù),配合優(yōu)化后的高性能多媒體計(jì)算集群,大幅度降低人工審核成本的同時(shí),提升了對(duì)內(nèi)容風(fēng)險(xiǎn)的防控能力。 阿里巴巴直播內(nèi)容風(fēng)險(xiǎn)防控中的AI力量 直播作為近來(lái)新興的互動(dòng)形態(tài)和今年阿里巴巴雙十一的一大亮點(diǎn),其內(nèi)容風(fēng)險(xiǎn)監(jiān)控是一個(gè)全新的課題,技術(shù)的挑戰(zhàn)非常大,管控難點(diǎn)主要包括業(yè)界缺乏成熟方案和標(biāo)準(zhǔn)、主播行為、直播內(nèi)容不可控、峰值...

    lvzishen 評(píng)論0 收藏0
  • 場(chǎng)景化封裝,一站式使用,普惠AI集成 ——阿里云發(fā)布智能媒體管理產(chǎn)品

    摘要:摘要導(dǎo)語(yǔ)近日,阿里云發(fā)布了智能媒體管理服務(wù),通過離線處理能力關(guān)聯(lián)授權(quán)的云存儲(chǔ),提供便捷的海量多媒體數(shù)據(jù)一鍵分析,并通過該分析過程構(gòu)建價(jià)值元數(shù)據(jù),更好支撐內(nèi)容檢索。標(biāo)準(zhǔn)統(tǒng)一,訪問接口統(tǒng)一為阿里云的標(biāo)準(zhǔn)。場(chǎng)景化一鍵式處理,提高易用性。 摘要: 導(dǎo)語(yǔ) 近日,阿里云發(fā)布了智能媒體管理(Intelligent Media Management)服務(wù), 通過離線處理能力關(guān)聯(lián)授權(quán)的云存儲(chǔ),提供便捷的...

    big_cat 評(píng)論0 收藏0

發(fā)表評(píng)論

0條評(píng)論

最新活動(dòng)
閱讀需要支付1元查看
<