Skip to content

Commit cdf5d80

Browse files
committed
first
0 parents  commit cdf5d80

File tree

332 files changed

+332953
-0
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

332 files changed

+332953
-0
lines changed

001_bodypix-worker-js/.gitignore

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
*~
2+
*#
3+
node_modules
4+
dist
5+
yarn-error.log

001_bodypix-worker-js/.npmignore

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
*~
2+
*#
3+
node_modules
4+
demo
5+
src
6+
yarn-error.log

001_bodypix-worker-js/package-lock.json

Lines changed: 4474 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

001_bodypix-worker-js/package.json

Lines changed: 46 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,46 @@
1+
{
2+
"name": "@dannadori/bodypix-worker-js",
3+
"version": "1.0.18",
4+
"description": "",
5+
"main": "dist/bodypix-worker.js",
6+
"scripts": {
7+
"test": "echo \"Error: no test specified\" && exit 1",
8+
"webpack": "npx webpack --config webpack.config.js",
9+
"clean": "rimraf dist/*",
10+
"build": "cp ../common/*.ts ./src;npm-run-all clean webpack"
11+
},
12+
"repository": {
13+
"type": "git",
14+
"url": "git+https://github.com/FLECT-DEV-TEAM/image-analyze-workers"
15+
},
16+
"keywords": [
17+
"webworker",
18+
"image processing",
19+
"tensorflowjs"
20+
],
21+
"author": "[email protected]",
22+
"license": "MIT",
23+
"bugs": {
24+
"url": "https://github.com/FLECT-DEV-TEAM/image-analyze-workers/issues"
25+
},
26+
"homepage": "https://github.com/FLECT-DEV-TEAM/image-analyze-workers#readme",
27+
"devDependencies": {
28+
"npm-run-all": "^4.1.5",
29+
"rimraf": "^3.0.2",
30+
"ts-loader": "^8.0.4",
31+
"tsconfig-paths": "^3.9.0",
32+
"typescript": "^4.0.3",
33+
"webpack": "^4.44.2",
34+
"webpack-cli": "^3.3.12",
35+
"worker-plugin": "^5.0.0"
36+
},
37+
"dependencies": {
38+
"@tensorflow-models/body-pix": "^2.0.5",
39+
"@tensorflow/tfjs": "^2.5.0",
40+
"@tensorflow/tfjs-backend-wasm": "^2.5.0",
41+
"@tensorflow/tfjs-converter": "~1.2.1",
42+
"@tensorflow/tfjs-core": "~1.2.1",
43+
"@types/node": "^14.11.2",
44+
"await-semaphore": "^0.1.3"
45+
}
46+
}
Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
/************************************************
2+
* THIS FILE SHOULD BE EDITED IN COMMON FOLDER. *
3+
************************************************/
4+
5+
export enum BrowserType {
6+
"MSIE",
7+
"EDGE",
8+
"CHROME",
9+
"SAFARI",
10+
"FIREFOX",
11+
"OPERA",
12+
"OTHER",
13+
}
14+
15+
export const getBrowserType = () => {
16+
var userAgent = window.navigator.userAgent.toLowerCase();
17+
if (userAgent.indexOf('msie') !== -1 || userAgent.indexOf('trident') !== -1) {
18+
return BrowserType.MSIE
19+
} else if (userAgent.indexOf('edge') !== -1) {
20+
return BrowserType.EDGE
21+
} else if (userAgent.indexOf('chrome') !== -1) {
22+
return BrowserType.CHROME
23+
} else if (userAgent.indexOf('safari') !== -1) {
24+
return BrowserType.SAFARI
25+
} else if (userAgent.indexOf('firefox') !== -1) {
26+
return BrowserType.FIREFOX
27+
} else if (userAgent.indexOf('opera') !== -1) {
28+
return BrowserType.OPERA
29+
} else {
30+
return BrowserType.OTHER
31+
}
32+
}

001_bodypix-worker-js/src/DemoUtil.ts

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
/************************************************
2+
* THIS FILE SHOULD BE EDITED IN COMMON FOLDER. *
3+
************************************************/
4+
5+
export const IMAGE_PATH = "https://www.sponichi.co.jp/entertainment/news/2019/10/04/jpeg/20191004s00041000331000p_view.jpg"
Lines changed: 183 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,183 @@
1+
import { WorkerResponse, WorkerCommand, BodypixFunctionType, BodyPixConfig, ModelConfigMobileNetV1_05, BodyPixOperatipnParams } from "./const"
2+
import * as bodyPix from '@tensorflow-models/body-pix'
3+
import { BrowserType, getBrowserType } from "./BrowserUtil";
4+
5+
export { ModelConfigResNet, ModelConfigMobileNetV1, ModelConfigMobileNetV1_05, BodypixFunctionType } from './const'
6+
export { BrowserType, getBrowserType} from './BrowserUtil';
7+
export { IMAGE_PATH } from "./DemoUtil"
8+
export {SemanticPersonSegmentation, SemanticPartSegmentation, PersonSegmentation, PartSegmentation} from '@tensorflow-models/body-pix'
9+
export { BodyPixInternalResolution } from '@tensorflow-models/body-pix/dist/types';
10+
11+
export const generateBodyPixDefaultConfig = ():BodyPixConfig => {
12+
const defaultConf:BodyPixConfig = {
13+
browserType : getBrowserType(),
14+
model : ModelConfigMobileNetV1_05,
15+
processOnLocal : false,
16+
}
17+
return defaultConf
18+
}
19+
20+
export const generateDefaultBodyPixParams = () =>{
21+
const defaultParams: BodyPixOperatipnParams = {
22+
type: BodypixFunctionType.SegmentPerson,
23+
segmentPersonParams:{
24+
flipHorizontal : false,
25+
internalResolution: "medium",
26+
segmentationThreshold: 0.7,
27+
maxDetections: 10,
28+
scoreThreshold: 0.3,
29+
nmsRadius: 20,
30+
},
31+
segmentPersonPartsParams:{
32+
flipHorizontal : false,
33+
internalResolution: "medium",
34+
segmentationThreshold: 0.7,
35+
maxDetections: 10,
36+
scoreThreshold: 0.3,
37+
nmsRadius: 20,
38+
},
39+
segmentMultiPersonParams:{
40+
flipHorizontal : false,
41+
internalResolution: "medium",
42+
segmentationThreshold: 0.7,
43+
maxDetections: 10,
44+
scoreThreshold: 0.3,
45+
nmsRadius: 20,
46+
minKeypointScore: 0.3,
47+
refineSteps:10
48+
},
49+
segmentMultiPersonPartsParams:{
50+
flipHorizontal : false,
51+
internalResolution: "medium",
52+
segmentationThreshold: 0.7,
53+
maxDetections: 10,
54+
scoreThreshold: 0.3,
55+
nmsRadius: 20,
56+
minKeypointScore: 0.3,
57+
refineSteps:10
58+
},
59+
processWidth : 300,
60+
processHeight : 300,
61+
62+
}
63+
return defaultParams
64+
}
65+
66+
class LocalBP {
67+
model: bodyPix.BodyPix | null = null
68+
canvas: HTMLCanvasElement = (()=>{
69+
const newCanvas = document.createElement("canvas")
70+
newCanvas.style.display="none"
71+
return newCanvas
72+
})()
73+
74+
init = (config: BodyPixConfig) => {
75+
return bodyPix.load(config.model).then(res => {
76+
console.log("bodypix loaded locally", config)
77+
this.model = res
78+
return
79+
})
80+
}
81+
82+
83+
predict = async (targetCanvas: HTMLCanvasElement, config:BodyPixConfig, params:BodyPixOperatipnParams) => {
84+
// ImageData作成
85+
const processWidth = (params.processWidth <= 0 || params.processHeight <= 0) ? targetCanvas.width : params.processWidth
86+
const processHeight = (params.processWidth <= 0 || params.processHeight <= 0) ? targetCanvas.height : params.processHeight
87+
88+
//console.log("process image size:", processWidth, processHeight)
89+
this.canvas.width = processWidth
90+
this.canvas.height = processHeight
91+
const ctx = this.canvas.getContext("2d")!
92+
ctx.drawImage(targetCanvas, 0, 0, processWidth, processHeight)
93+
const newImg = ctx.getImageData(0, 0, processWidth, processHeight)
94+
95+
let prediction
96+
if(params.type === BodypixFunctionType.SegmentPerson){
97+
prediction = await this.model!.segmentPerson(newImg, params.segmentPersonParams)
98+
}else if(params.type === BodypixFunctionType.SegmentPersonParts){
99+
prediction = await this.model!.segmentPersonParts(newImg, params.segmentPersonPartsParams)
100+
}else if(params.type === BodypixFunctionType.SegmentMultiPerson){
101+
prediction = await this.model!.segmentMultiPerson(newImg, params.segmentMultiPersonParams)
102+
}else if(params.type === BodypixFunctionType.SegmentMultiPersonParts){
103+
prediction = await this.model!.segmentMultiPersonParts(newImg, params.segmentMultiPersonPartsParams)
104+
}else{// segmentPersonに倒す
105+
prediction = await this.model!.segmentPerson(newImg, params.segmentPersonParams)
106+
}
107+
return prediction
108+
}
109+
}
110+
111+
export class BodypixWorkerManager {
112+
private workerBP: Worker | null = null
113+
114+
config:BodyPixConfig = generateBodyPixDefaultConfig()
115+
private localBP = new LocalBP()
116+
117+
init(config:BodyPixConfig|null = null) {
118+
if(config != null){
119+
this.config = config
120+
}
121+
if(this.workerBP){
122+
this.workerBP.terminate()
123+
}
124+
125+
if(this.config.browserType === BrowserType.SAFARI || this.config.processOnLocal == true){
126+
// safariはwebworkerでWebGLが使えないのでworkerは使わない。
127+
return new Promise((onResolve, onFail) => {
128+
this.localBP.init(this.config!).then(() => {
129+
onResolve()
130+
})
131+
})
132+
}
133+
134+
135+
this.workerBP = new Worker('./workerBP.ts', { type: 'module' })
136+
137+
this.workerBP!.postMessage({ message: WorkerCommand.INITIALIZE, config: this.config })
138+
return new Promise((onResolve, onFail) => {
139+
this.workerBP!.onmessage = (event) => {
140+
if (event.data.message === WorkerResponse.INITIALIZED) {
141+
console.log("WORKERSS INITIALIZED")
142+
onResolve()
143+
} else {
144+
console.log("Bodypix Initialization something wrong..")
145+
onFail(event)
146+
}
147+
}
148+
})
149+
}
150+
151+
predict(targetCanvas: HTMLCanvasElement, params:BodyPixOperatipnParams) {
152+
if(this.config.browserType === BrowserType.SAFARI || this.config.processOnLocal == true){
153+
const p = new Promise(async (onResolve: (v: any) => void, onFail) => {
154+
const prediction = await this.localBP.predict(targetCanvas, this.config, params)
155+
onResolve(prediction)
156+
})
157+
return p
158+
}else{
159+
const offscreen = new OffscreenCanvas(targetCanvas.width, targetCanvas.height)
160+
const offctx = offscreen.getContext("2d")!
161+
offctx.drawImage(targetCanvas, 0, 0, targetCanvas.width, targetCanvas.height)
162+
const imageBitmap = offscreen.transferToImageBitmap()
163+
const uid = performance.now()
164+
const p = new Promise((onResolve: (v:any) => void, onFail) => {
165+
this.workerBP!.postMessage({
166+
message: WorkerCommand.PREDICT, uid: uid,
167+
params:params, image: imageBitmap,
168+
config:this.config
169+
}, [imageBitmap])
170+
171+
this.workerBP!.onmessage = (event) => {
172+
if (event.data.message === WorkerResponse.PREDICTED && event.data.uid === uid) {
173+
onResolve(event.data.prediction)
174+
} else {
175+
console.log("Bodypix Prediction something wrong..")
176+
onFail(event)
177+
}
178+
}
179+
})
180+
return p
181+
}
182+
}
183+
}

001_bodypix-worker-js/src/const.ts

Lines changed: 56 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,56 @@
1+
import { ModelConfig, PersonInferenceConfig, MultiPersonInstanceInferenceConfig } from '@tensorflow-models/body-pix/dist/body_pix_model';
2+
import { BrowserType } from './BrowserUtil';
3+
4+
5+
export const WorkerCommand = {
6+
INITIALIZE : 'initialize',
7+
PREDICT : 'predict',
8+
}
9+
10+
export const WorkerResponse = {
11+
INITIALIZED : 'initialized',
12+
PREDICTED : 'predicted',
13+
}
14+
15+
export interface BodyPixConfig{
16+
browserType : BrowserType
17+
model : ModelConfig
18+
processOnLocal : boolean
19+
}
20+
21+
export const ModelConfigResNet: ModelConfig = {
22+
architecture: 'ResNet50',
23+
outputStride: 32,
24+
quantBytes: 2
25+
}
26+
export const ModelConfigMobileNetV1: ModelConfig = {
27+
architecture: 'MobileNetV1',
28+
outputStride: 16,
29+
multiplier: 0.75,
30+
quantBytes: 2
31+
}
32+
export const ModelConfigMobileNetV1_05: ModelConfig = {
33+
architecture: 'MobileNetV1',
34+
outputStride: 16,
35+
multiplier: 0.5,
36+
quantBytes: 2
37+
}
38+
39+
export interface BodyPixOperatipnParams{
40+
type: BodypixFunctionType
41+
segmentPersonParams: PersonInferenceConfig
42+
segmentPersonPartsParams: PersonInferenceConfig
43+
segmentMultiPersonParams: MultiPersonInstanceInferenceConfig
44+
segmentMultiPersonPartsParams: MultiPersonInstanceInferenceConfig
45+
processWidth : number
46+
processHeight : number
47+
48+
}
49+
50+
export enum BodypixFunctionType{
51+
SegmentPerson,
52+
SegmentMultiPerson,
53+
SegmentPersonParts,
54+
SegmentMultiPersonParts
55+
}
56+

0 commit comments

Comments
 (0)