Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
F
face
Project
Overview
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
Иван Кубота
face
Commits
3f1826ab
Commit
3f1826ab
authored
Jul 14, 2018
by
vincent
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
added examples for mtcnn face detection + added getters to FaceDetection
parent
2b794bc3
Show whitespace changes
Inline
Side-by-side
Showing
6 changed files
with
196 additions
and
44 deletions
+196
-44
commons.js
examples/public/commons.js
+9
-2
server.js
examples/server.js
+1
-0
mtcnnFaceDetection.html
examples/views/mtcnnFaceDetection.html
+12
-11
mtcnnFaceDetectionVideo.html
examples/views/mtcnnFaceDetectionVideo.html
+24
-26
mtcnnFaceDetectionWebcam.html
examples/views/mtcnnFaceDetectionWebcam.html
+125
-0
FaceDetection.ts
src/FaceDetection.ts
+25
-5
No files found.
examples/public/commons.js
View file @
3f1826ab
...
...
@@ -123,6 +123,10 @@ function renderNavBar(navbarId, exampleUri) {
name
:
'MTCNN Face Detection Video'
},
{
uri
:
'mtcnn_face_detection_webcam'
,
name
:
'MTCNN Face Detection Webcam'
},
{
uri
:
'batch_face_landmarks'
,
name
:
'Batch Face Landmarks'
},
...
...
@@ -159,7 +163,7 @@ function renderNavBar(navbarId, exampleUri) {
githubLink
.
id
=
'github-link'
githubLink
.
href
=
'https://github.com/justadudewhohacks/face-api.js'
const
h5
=
document
.
createElement
(
'h5'
)
h5
.
innerHTML
=
'face-api.js'
//'If you like this project, feel free to leave a star on github :)'
h5
.
innerHTML
=
'face-api.js'
githubLink
.
appendChild
(
h5
)
const
githubLinkIcon
=
document
.
createElement
(
'img'
)
githubLinkIcon
.
src
=
'github_link_icon.png'
...
...
@@ -176,7 +180,10 @@ function renderNavBar(navbarId, exampleUri) {
const
a
=
document
.
createElement
(
'a'
)
a
.
classList
.
add
(
'waves-effect'
,
'waves-light'
)
a
.
href
=
ex
.
uri
a
.
innerHTML
=
ex
.
name
const
span
=
document
.
createElement
(
'span'
)
span
.
innerHTML
=
ex
.
name
span
.
style
.
whiteSpace
=
'nowrap'
a
.
appendChild
(
span
)
li
.
appendChild
(
a
)
menuContent
.
appendChild
(
li
)
})
...
...
examples/server.js
View file @
3f1826ab
...
...
@@ -26,6 +26,7 @@ app.get('/face_alignment', (req, res) => res.sendFile(path.join(viewsDir, 'faceA
app
.
get
(
'/detect_and_recognize_faces'
,
(
req
,
res
)
=>
res
.
sendFile
(
path
.
join
(
viewsDir
,
'detectAndRecognizeFaces.html'
)))
app
.
get
(
'/mtcnn_face_detection'
,
(
req
,
res
)
=>
res
.
sendFile
(
path
.
join
(
viewsDir
,
'mtcnnFaceDetection.html'
)))
app
.
get
(
'/mtcnn_face_detection_video'
,
(
req
,
res
)
=>
res
.
sendFile
(
path
.
join
(
viewsDir
,
'mtcnnFaceDetectionVideo.html'
)))
app
.
get
(
'/mtcnn_face_detection_webcam'
,
(
req
,
res
)
=>
res
.
sendFile
(
path
.
join
(
viewsDir
,
'mtcnnFaceDetectionWebcam.html'
)))
app
.
get
(
'/batch_face_landmarks'
,
(
req
,
res
)
=>
res
.
sendFile
(
path
.
join
(
viewsDir
,
'batchFaceLandmarks.html'
)))
app
.
get
(
'/batch_face_recognition'
,
(
req
,
res
)
=>
res
.
sendFile
(
path
.
join
(
viewsDir
,
'batchFaceRecognition.html'
)))
...
...
examples/views/mtcnnFaceDetection.html
View file @
3f1826ab
...
...
@@ -52,10 +52,10 @@
</div>
<script>
let
minFaceSize
=
50
//20 //
let
scaleFactor
=
0.709
// 0.2
let
maxNumScales
=
10
// 0.2
let
stage1Threshold
=
0.
6
let
minFaceSize
=
50
let
scaleFactor
=
0.709
let
maxNumScales
=
10
let
stage1Threshold
=
0.
7
let
stage2Threshold
=
0.7
let
stage3Threshold
=
0.7
let
mtcnn
...
...
@@ -85,13 +85,15 @@
canvas
.
width
=
width
canvas
.
height
=
height
const
scoreThresholds
=
[
stage1Threshold
,
stage2Threshold
,
stage3Threshold
]
const
{
results
,
stats
}
=
await
mtcnn
.
forwardWithStats
(
inputImgEl
,
minFaceSize
,
scaleFactor
,
maxNumScales
,
scoreThresholds
)
console
.
log
(
stats
)
const
mtcnnParams
=
{
minFaceSize
,
scaleFactor
,
maxNumScales
,
scoreThresholds
:
[
stage1Threshold
,
stage2Threshold
,
stage3Threshold
]
}
const
results
=
await
faceapi
.
mtcnn
(
inputImgEl
,
mtcnnParams
)
if
(
results
)
{
const
{
faceDetection
,
faceLandmarks
}
=
results
results
.
forEach
(({
faceDetection
,
faceLandmarks
})
=>
{
faceapi
.
drawDetection
(
'overlay'
,
faceDetection
.
forSize
(
width
,
height
))
faceapi
.
drawLandmarks
(
'overlay'
,
faceLandmarks
.
forSize
(
width
,
height
),
{
lineWidth
:
4
,
color
:
'red'
})
...
...
@@ -106,8 +108,7 @@
}
async
function
run
()
{
const
weightsBuffer
=
await
(
await
fetch
(
'/uncompressed/mtcnn_model.weights'
)).
arrayBuffer
()
mtcnn
=
faceapi
.
mtcnn
(
new
Float32Array
(
weightsBuffer
))
await
faceapi
.
loadMtcnnModel
(
'/'
)
$
(
'#loader'
).
hide
()
onSelectionChanged
(
$
(
'#selectList select'
).
val
())
}
...
...
examples/views/mtcnnFaceDetectionVideo.html
View file @
3f1826ab
...
...
@@ -20,18 +20,18 @@
</div>
<div
class=
"row side-by-side"
>
<div
class=
"row"
>
<label
for=
"min
Confidence"
>
Min Confidenc
e:
</label>
<input
disabled
value=
"
0.7"
id=
"minConfidenc
e"
type=
"text"
class=
"bold"
>
<label
for=
"min
FaceSize"
>
Minimum Face Siz
e:
</label>
<input
disabled
value=
"
80"
id=
"minFaceSiz
e"
type=
"text"
class=
"bold"
>
</div>
<button
class=
"waves-effect waves-light btn"
onclick=
"onDecrease
Threshold
()"
onclick=
"onDecrease
MinFaceSize
()"
>
<i
class=
"material-icons left"
>
-
</i>
</button>
<button
class=
"waves-effect waves-light btn"
onclick=
"onIncrease
Threshold
()"
onclick=
"onIncrease
MinFaceSize
()"
>
<i
class=
"material-icons left"
>
+
</i>
</button>
...
...
@@ -49,29 +49,26 @@
</div>
<script>
let
modelLoaded
=
false
let
minFaceSize
=
80
let
scaleFactor
=
0.709
let
maxNumScales
=
10
let
minConfidence
=
0.9
let
stage1Threshold
=
0.7
let
stage2Threshold
=
0.7
let
stage3Threshold
=
0.7
let
modelLoaded
=
false
let
result
let
forwardTimes
=
[]
function
onIncrease
Threshold
()
{
min
Confidence
=
Math
.
min
(
faceapi
.
round
(
minConfidence
+
0.1
),
1.
0
)
$
(
'#min
Confidence'
).
val
(
minConfidenc
e
)
function
onIncrease
MinFaceSize
()
{
min
FaceSize
=
Math
.
min
(
faceapi
.
round
(
minFaceSize
+
20
),
20
0
)
$
(
'#min
FaceSize'
).
val
(
minFaceSiz
e
)
}
function
onDecrease
Threshold
()
{
min
Confidence
=
Math
.
max
(
faceapi
.
round
(
minConfidence
-
0.1
),
0.1
)
$
(
'#min
Confidence'
).
val
(
minConfidenc
e
)
function
onDecrease
MinFaceSize
()
{
min
FaceSize
=
Math
.
max
(
faceapi
.
round
(
minFaceSize
-
20
),
20
)
$
(
'#min
FaceSize'
).
val
(
minFaceSiz
e
)
}
function
displayTimeStats
(
timeInMs
)
{
$
(
'#time'
).
val
(
`
${
timeInMs
}
ms`
)
$
(
'#fps'
).
val
(
`
${
faceapi
.
round
(
1000
/
timeInMs
)}
`
)
function
updateTimeStats
(
timeInMs
)
{
forwardTimes
=
[
timeInMs
].
concat
(
forwardTimes
).
slice
(
0
,
30
)
const
avgTimeInMs
=
forwardTimes
.
reduce
((
total
,
t
)
=>
total
+
t
)
/
forwardTimes
.
length
$
(
'#time'
).
val
(
`
${
Math
.
round
(
avgTimeInMs
)}
ms`
)
$
(
'#fps'
).
val
(
`
${
faceapi
.
round
(
1000
/
avgTimeInMs
)}
`
)
}
async
function
onPlay
(
videoEl
)
{
...
...
@@ -83,13 +80,15 @@
canvas
.
width
=
width
canvas
.
height
=
height
const
scoreThresholds
=
[
stage1Threshold
,
stage2Threshold
,
stage3Threshold
]
const
mtcnnParams
=
{
minFaceSize
}
const
ts
=
Date
.
now
()
const
{
results
,
stats
}
=
await
mtcnn
.
forwardWithStats
(
videoEl
,
minFaceSize
,
scaleFactor
,
maxNumScales
,
scoreThreshold
s
)
display
TimeStats
(
Date
.
now
()
-
ts
)
const
results
=
await
faceapi
.
mtcnn
(
videoEl
,
mtcnnParam
s
)
update
TimeStats
(
Date
.
now
()
-
ts
)
if
(
results
)
{
const
{
faceDetection
,
faceLandmarks
}
=
results
results
.
forEach
(({
faceDetection
,
faceLandmarks
})
=>
{
if
(
faceDetection
.
score
<
minConfidence
)
{
return
...
...
@@ -102,8 +101,7 @@
}
async
function
run
()
{
const
weightsBuffer
=
await
(
await
fetch
(
'/uncompressed/mtcnn_model.weights'
)).
arrayBuffer
()
mtcnn
=
faceapi
.
mtcnn
(
new
Float32Array
(
weightsBuffer
))
await
faceapi
.
loadMtcnnModel
(
'/'
)
modelLoaded
=
true
onPlay
(
$
(
'#inputVideo'
).
get
(
0
))
$
(
'#loader'
).
hide
()
...
...
examples/views/mtcnnFaceDetectionWebcam.html
0 → 100644
View file @
3f1826ab
<!DOCTYPE html>
<html>
<head>
<script
src=
"face-api.js"
></script>
<script
src=
"commons.js"
></script>
<link
rel=
"stylesheet"
href=
"styles.css"
>
<link
rel=
"stylesheet"
href=
"https://cdnjs.cloudflare.com/ajax/libs/materialize/0.100.2/css/materialize.css"
>
<script
type=
"text/javascript"
src=
"https://code.jquery.com/jquery-2.1.1.min.js"
></script>
<script
src=
"https://cdnjs.cloudflare.com/ajax/libs/materialize/0.100.2/js/materialize.min.js"
></script>
</head>
<body>
<div
id=
"navbar"
></div>
<div
class=
"center-content page-container"
>
<div
class=
"progress"
id=
"loader"
>
<div
class=
"indeterminate"
></div>
</div>
<div
style=
"position: relative"
class=
"margin"
>
<video
onplay=
"onPlay(this)"
id=
"inputVideo"
autoplay
muted
></video>
<canvas
id=
"overlay"
/>
</div>
<div
class=
"row side-by-side"
>
<div
class=
"row"
>
<label
for=
"minFaceSize"
>
Minimum Face Size:
</label>
<input
disabled
value=
"200"
id=
"minFaceSize"
type=
"text"
class=
"bold"
>
</div>
<button
class=
"waves-effect waves-light btn"
onclick=
"onDecreaseMinFaceSize()"
>
<i
class=
"material-icons left"
>
-
</i>
</button>
<button
class=
"waves-effect waves-light btn"
onclick=
"onIncreaseMinFaceSize()"
>
<i
class=
"material-icons left"
>
+
</i>
</button>
</div>
<div
class=
"row side-by-side"
>
<div
class=
"row"
>
<label
for=
"time"
>
Time:
</label>
<input
disabled
value=
"-"
id=
"time"
type=
"text"
class=
"bold"
>
</div>
<div
class=
"row"
>
<label
for=
"fps"
>
Estimated Fps:
</label>
<input
disabled
value=
"-"
id=
"fps"
type=
"text"
class=
"bold"
>
</div>
</div>
</div>
<script>
let
modelLoaded
=
false
let
minFaceSize
=
200
let
minConfidence
=
0.9
let
forwardTimes
=
[]
function
onIncreaseMinFaceSize
()
{
minFaceSize
=
Math
.
min
(
faceapi
.
round
(
minFaceSize
+
50
),
300
)
$
(
'#minFaceSize'
).
val
(
minFaceSize
)
}
function
onDecreaseMinFaceSize
()
{
minFaceSize
=
Math
.
max
(
faceapi
.
round
(
minFaceSize
-
50
),
50
)
$
(
'#minFaceSize'
).
val
(
minFaceSize
)
}
function
updateTimeStats
(
timeInMs
)
{
forwardTimes
=
[
timeInMs
].
concat
(
forwardTimes
).
slice
(
0
,
30
)
const
avgTimeInMs
=
forwardTimes
.
reduce
((
total
,
t
)
=>
total
+
t
)
/
forwardTimes
.
length
$
(
'#time'
).
val
(
`
${
Math
.
round
(
avgTimeInMs
)}
ms`
)
$
(
'#fps'
).
val
(
`
${
faceapi
.
round
(
1000
/
avgTimeInMs
)}
`
)
}
async
function
onPlay
(
videoEl
)
{
if
(
videoEl
.
paused
||
videoEl
.
ended
||
!
modelLoaded
)
return
false
const
{
width
,
height
}
=
faceapi
.
getMediaDimensions
(
videoEl
)
const
canvas
=
$
(
'#overlay'
).
get
(
0
)
canvas
.
width
=
width
canvas
.
height
=
height
const
mtcnnParams
=
{
minFaceSize
}
const
c
=
faceapi
.
createCanvas
({
width
:
width
,
height
:
height
})
c
.
getContext
(
'2d'
).
drawImage
(
videoEl
,
0
,
0
)
const
{
results
,
stats
}
=
await
faceapi
.
nets
.
mtcnn
.
forwardWithStats
(
c
,
mtcnnParams
)
updateTimeStats
(
stats
.
total
)
if
(
results
)
{
results
.
forEach
(({
faceDetection
,
faceLandmarks
})
=>
{
if
(
faceDetection
.
score
<
minConfidence
)
{
return
}
faceapi
.
drawDetection
(
'overlay'
,
faceDetection
.
forSize
(
width
,
height
))
faceapi
.
drawLandmarks
(
'overlay'
,
faceLandmarks
.
forSize
(
width
,
height
),
{
lineWidth
:
4
,
color
:
'red'
})
})
}
setTimeout
(()
=>
onPlay
(
videoEl
))
}
async
function
run
()
{
await
faceapi
.
loadMtcnnModel
(
'/'
)
modelLoaded
=
true
const
videoEl
=
$
(
'#inputVideo'
).
get
(
0
)
navigator
.
getUserMedia
(
{
video
:
{}
},
stream
=>
videoEl
.
srcObject
=
stream
,
err
=>
console
.
error
(
err
)
)
$
(
'#loader'
).
hide
()
}
$
(
document
).
ready
(
function
()
{
renderNavBar
(
'#navbar'
,
'mtcnn_face_detection_webcam'
)
run
()
})
</script>
</body>
</html>
\ No newline at end of file
src/FaceDetection.ts
View file @
3f1826ab
...
...
@@ -24,23 +24,23 @@ export class FaceDetection {
)
}
public
get
Score
()
{
public
get
score
():
number
{
return
this
.
_score
}
public
get
Box
()
{
public
get
box
():
Rect
{
return
this
.
_box
}
public
get
ImageWidth
()
{
public
get
imageWidth
():
number
{
return
this
.
_imageWidth
}
public
get
ImageHeight
()
{
public
get
imageHeight
():
number
{
return
this
.
_imageHeight
}
public
get
RelativeBox
()
{
public
get
relativeBox
():
Rect
{
return
new
Rect
(
this
.
_box
.
x
/
this
.
_imageWidth
,
this
.
_box
.
y
/
this
.
_imageHeight
,
...
...
@@ -49,6 +49,26 @@ export class FaceDetection {
)
}
public
getScore
()
{
return
this
.
score
}
public
getBox
()
{
return
this
.
box
}
public
getImageWidth
()
{
return
this
.
imageWidth
}
public
getImageHeight
()
{
return
this
.
imageHeight
}
public
getRelativeBox
()
{
return
this
.
relativeBox
}
public
forSize
(
width
:
number
,
height
:
number
):
FaceDetection
{
return
new
FaceDetection
(
this
.
_score
,
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment