Skip to content
Permalink
Browse files

v5.1.5 - 2020.03.17:

+ Added an ASM.js export. We do now support a manual ASM.js fallback.
  Since WebAssembly is available almost everywhere, there is no automatic checking/switching.
+ Added a nodejs example. There is an issue with loading more than 6 model chunks for 68l, which leads to wrong results, not sure why yet.
  • Loading branch information
Marcel Klammer
Marcel Klammer committed Mar 17, 2020
1 parent 10064e3 commit b8a69b8b9271bb9b5d41eeb55a281b3946513f00
@@ -1,4 +1,4 @@
# Beyond Reality Face SDK - v5.1.0 (BRFv5) - Platform: Browser
# Beyond Reality Face SDK - v5.1.5 (BRFv5) - Platform: Browser

### What is BRFv5?

@@ -161,6 +161,12 @@ When will the other platforms be available.
### Release notes
v5.1.5 - 17th March 2020
+ Added an ASM.js export. We do now support a manual ASM.js fallback.
Since WebAssembly is available almost everywhere, there is no automatic checking/switching.
+ Added a nodejs example. There is an issue with loading more than 6 model chunks for 68l, which leads to wrong results, not sure why yet.
v5.1.3 - 29th January 2020
+ Version bump for emscripten to v1.39.6 - upstream
@@ -0,0 +1,190 @@
const { brfv5Module } = require('./js/brfv5/brfv5_js_tk170320_v5.1.5_trial_nodejs')

const fs = require('fs')
const pixels = require('image-pixels')

const imageURL = './assets/tracking/brfv5_portrait_marcel.jpg'

let imageBuffer = null; // file buffer
let imageData = null; // pixel buffer

// Set the BRFv5 library name here, also set your own appId for reference.

const _libraryName = 'brfv5_js_tk170320_v5.1.5_trial.brfv5'
const _appId = 'brfv5.nodejs.minimal' // (mandatory): 8 to 64 characters, a-z . 0-9 allowed
const brfv5 = {} // The library namespace.

// References to the video and canvas.
// const _webcam = document.getElementById('_webcam')
// const _imageData = document.getElementById('_imageData')

// Those variables will be retrieved from the stream and the library.
let _brfv5Manager = null
let _brfv5Config = null
let _width = 0
let _height = 0

// loadBRFv5Model and openCamera are being done simultaneously thanks to Promises. Both call
// configureTracking which only gets executed once both Promises were successful. Once configured
// trackFaces will do the tracking work and draw the results.

const loadBRFv5Model = (modelName, numChunksToLoad, pathToModels = '', appId = null, onProgress = null) => {

console.log('loadBRFv5Model')

if(!modelName) { throw 'Please provide a modelName.' }

return new Promise((resolve, reject) => {

if(_brfv5Manager && _brfv5Config) {

resolve({ brfv5Manager: _brfv5Manager, brfv5Config: _brfv5Config })

} else {

try {

brfv5.appId = appId ? appId : _appId
brfv5.binaryLocation = pathToModels + _libraryName
brfv5.modelLocation = pathToModels + modelName + '_c'
brfv5.modelChunks = numChunksToLoad // 4, 6, 8
brfv5.binaryProgress = onProgress
brfv5.binaryError = (e) => { reject(e) }
brfv5.onInit = (brfv5Manager, brfv5Config) => {

_brfv5Manager = brfv5Manager
_brfv5Config = brfv5Config

resolve({ brfv5Manager: _brfv5Manager, brfv5Config: _brfv5Config })
}

brfv5Module(brfv5)

} catch(e) {

reject(e)
}
}
})
}

const loadImage = async (imageURL) => {

console.log('loadImage: ', imageURL)

imageBuffer = fs.readFileSync(imageURL);

const { data, width, height } = await pixels(imageBuffer)

imageData = data;

return { width: width, height: height };
}

const configureTracking = () => {

if(_brfv5Config !== null && _width > 0) {

// Camera stream and BRFv5 are ready. Now configure. Internal defaults are set for a 640x480 resolution.
// So the following isn't really necessary.

const brfv5Config = _brfv5Config
const imageWidth = _width
const imageHeight = _height

const inputSize = imageWidth > imageHeight ? imageHeight : imageWidth

// Setup image data dimensions

brfv5Config.imageConfig.inputWidth = imageWidth
brfv5Config.imageConfig.inputHeight = imageHeight

const sizeFactor = inputSize / 480.0

// Set face detection region of interest and parameters scaled to the image base size.

brfv5Config.faceDetectionConfig.regionOfInterest.setTo(0, 0, imageWidth, imageHeight)

brfv5Config.faceDetectionConfig.minFaceSize = 144 * sizeFactor
brfv5Config.faceDetectionConfig.maxFaceSize = 480 * sizeFactor

if(imageWidth < imageHeight) {

// Portrait mode: probably smartphone, faces tend to be closer to the camera, processing time is an issue,
// so save a bit of time and increase minFaceSize.

brfv5Config.faceDetectionConfig.minFaceSize = 240 * sizeFactor
}

// Set face tracking region of interest and parameters scaled to the image base size.

brfv5Config.faceTrackingConfig.regionOfInterest.setTo(0, 0, imageWidth, imageHeight)

brfv5Config.faceTrackingConfig.minFaceScaleStart = 50.0 * sizeFactor
brfv5Config.faceTrackingConfig.maxFaceScaleStart = 320.0 * sizeFactor

brfv5Config.faceTrackingConfig.minFaceScaleReset = 35.0 * sizeFactor
brfv5Config.faceTrackingConfig.maxFaceScaleReset = 420.0 * sizeFactor

brfv5Config.faceTrackingConfig.confidenceThresholdReset = 0.001

brfv5Config.faceTrackingConfig.enableStabilizer = true

brfv5Config.faceTrackingConfig.maxRotationXReset = 35.0
brfv5Config.faceTrackingConfig.maxRotationYReset = 45.0
brfv5Config.faceTrackingConfig.maxRotationZReset = 34.0

brfv5Config.faceTrackingConfig.numTrackingPasses = 3
brfv5Config.faceTrackingConfig.enableFreeRotation = true
brfv5Config.faceTrackingConfig.maxRotationZReset = 999.0

brfv5Config.faceTrackingConfig.numFacesToTrack = 1
brfv5Config.enableFaceTracking = true

// console.log('configureTracking:', _brfv5Config)

_brfv5Manager.configure(_brfv5Config)

trackFaces()
}
}

const trackFaces = () => {

if(!_brfv5Manager || !_brfv5Config) { return }

_brfv5Manager.update({ width: _width, height: _height, data: imageData })

const faces = _brfv5Manager.getFaces()

for(let i = 0; i < faces.length; i++) {

console.log(faces[i].bounds)
}
}

// TODO: warum geht 7 und 8 nicht bei 68l? Memory issue in nodejs? Not sure about it.
// for 68l, use 6 max model chunks
// for 42l, use 8 max model chunks
loadBRFv5Model('68l', 6, './js/brfv5/models/', _appId,
(progress) => { console.log(progress) }).then(({ brfv5Manager, brfv5Config }) => {

console.log('loadBRFv5Model: done')

_brfv5Manager = brfv5Manager
_brfv5Config = brfv5Config

console.log(brfv5)

loadImage(imageURL).then(({ width, height }) => {

console.log('loadImage: done: ' + width + 'x' + height)

_width = width
_height = height

configureTracking()

}).catch((e) => { if(e) { console.error('loadImage failed: ', e) } })

}).catch((e) => { console.error('BRFv5 failed: ', e) })
@@ -1,9 +1,12 @@
// Set the BRFv5 import and library name here.
// Also set your own appId for reference.

import { brfv5Module } from './brfv5_js_tk290120_v5.1.3_trial.js'
import { brfv5Module } from './brfv5_js_tk170320_v5.1.5_trial.js' // WebAssembly is available is every major browser, no need for asm.js
// import { brfv5Module } from './brfv5_js_tk170320_v5.1.5_trial.asm.js' // .asm.js is a manual possibility to load asm.js binaries

const _libraryName = 'brfv5_js_tk170320_v5.1.5_trial.brfv5' // for WebAssembly
// const _libraryName = 'brfv5_js_tk170320_v5.1.5_trial.asm.brfv5' // for asm.js

const _libraryName = 'brfv5_js_tk290120_v5.1.3_trial.brfv5'
const _appId = 'brfv5.browser.examples' // (mandatory): 8 to 64 characters, a-z . 0-9 allowed

export const brfv5 = {}
@@ -0,0 +1,58 @@
// Set the BRFv5 import and library name here.
// Also set your own appId for reference.

// THIS FILE IS THE SAME AS brfv5__init.js BUT PREPARED TO USE ASMJS BINARIES. YOU CAN STILL USE brfv5__init.js AND SWAP THE FILE NAMES!

// import { brfv5Module } from './brfv5_js_tk170320_v5.1.5_trial.js' // WebAssembly is available is every major browser, no need for asm.js
import { brfv5Module } from './brfv5_js_tk170320_v5.1.5_trial.asm.js' // .asm.js is a manual possibility to load asm.js binaries

// const _libraryName = 'brfv5_js_tk170320_v5.1.5_trial.brfv5' // for WebAssembly
const _libraryName = 'brfv5_js_tk170320_v5.1.5_trial.asm.brfv5' // for asm.js

const _appId = 'brfv5.browser.examples' // (mandatory): 8 to 64 characters, a-z . 0-9 allowed

export const brfv5 = {}

let _brfv5Manager = null
let _brfv5Config = null

// numChunksToLoad: can be anything from 4 to 8.
export const loadBRFv5Model = (modelName, numChunksToLoad, pathToModels = '', appId = null, onProgress = null) => {

if(!modelName) { throw 'Please provide a modelName.' }

return new Promise((resolve, reject) => {

if(_brfv5Manager && _brfv5Config) {

resolve({ brfv5Manager: _brfv5Manager, brfv5Config: _brfv5Config })

} else {

try {

brfv5.appId = appId ? appId : _appId
brfv5.binaryLocation = pathToModels + _libraryName
brfv5.modelLocation = pathToModels + modelName + '_c'
brfv5.modelChunks = numChunksToLoad // 4, 6, 8
brfv5.binaryProgress = onProgress
brfv5.binaryError = (e) => { reject(e) }
brfv5.onInit = (brfv5Manager, brfv5Config) => {

_brfv5Manager = brfv5Manager
_brfv5Config = brfv5Config

resolve({ brfv5Manager: _brfv5Manager, brfv5Config: _brfv5Config })
}

brfv5Module(brfv5)

} catch(e) {

reject(e)
}
}
})
}

export default { loadBRFv5Model, brfv5 }

0 comments on commit b8a69b8

Please sign in to comment.
You can’t perform that action at this time.