Browse Source

fix(facial-expressions): set screen size in worker and add constants for worker message types (#10678)

* fix(facial-expressions): set window screen size from worker with the value from main thread

* fix(facial-expressions): refactor worker and add constants for message types
master
Gabriel Borlea 3 years ago
parent
commit
fa9f4588c2
No account linked to committer's email address

+ 14
- 15
react/features/facial-recognition/actions.js View File

@@ -13,8 +13,10 @@ import {
13 13
     STOP_FACIAL_RECOGNITION
14 14
 } from './actionTypes';
15 15
 import {
16
-    CPU_TIME_INTERVAL,
17
-    WEBGL_TIME_INTERVAL,
16
+    CLEAR_TIMEOUT,
17
+    FACIAL_EXPRESSION_MESSAGE,
18
+    INIT_WORKER,
19
+    INTERVAL_MESSAGE,
18 20
     WEBHOOK_SEND_TIME_INTERVAL
19 21
 } from './constants';
20 22
 import { sendDataToWorker, sendFacialExpressionsWebhook } from './functions';
@@ -82,19 +84,12 @@ export function loadWorker() {
82 84
 
83 85
             // receives a message indicating what type of backend tfjs decided to use.
84 86
             // it is received after as a response to the first message sent to the worker.
85
-            if (type === 'tf-backend' && value) {
86
-                let detectionTimeInterval = -1;
87
-
88
-                if (value === 'webgl') {
89
-                    detectionTimeInterval = WEBGL_TIME_INTERVAL;
90
-                } else if (value === 'cpu') {
91
-                    detectionTimeInterval = CPU_TIME_INTERVAL;
92
-                }
93
-                dispatch(setDetectionTimeInterval(detectionTimeInterval));
87
+            if (type === INTERVAL_MESSAGE) {
88
+                value && dispatch(setDetectionTimeInterval(value));
94 89
             }
95 90
 
96 91
             // receives a message with the predicted facial expression.
97
-            if (type === 'facial-expression') {
92
+            if (type === FACIAL_EXPRESSION_MESSAGE) {
98 93
                 sendDataToWorker(worker, imageCapture);
99 94
                 if (!value) {
100 95
                     return;
@@ -118,8 +113,12 @@ export function loadWorker() {
118 113
             }
119 114
         };
120 115
         worker.postMessage({
121
-            id: 'SET_MODELS_URL',
122
-            url: baseUrl
116
+            type: INIT_WORKER,
117
+            url: baseUrl,
118
+            windowScreenSize: window.screen ? {
119
+                width: window.screen.width,
120
+                height: window.screen.height
121
+            } : undefined
123 122
         });
124 123
         dispatch(startFacialRecognition());
125 124
     };
@@ -187,7 +186,7 @@ export function stopFacialRecognition() {
187 186
         }
188 187
         imageCapture = null;
189 188
         worker.postMessage({
190
-            id: 'CLEAR_TIMEOUT'
189
+            type: CLEAR_TIMEOUT
191 190
         });
192 191
 
193 192
         if (lastFacialExpression && lastFacialExpressionTimestamp) {

+ 29
- 0
react/features/facial-recognition/constants.js View File

@@ -27,3 +27,32 @@ export const CPU_TIME_INTERVAL = 6000;
27 27
  * Time is ms used for sending expression.
28 28
  */
29 29
 export const WEBHOOK_SEND_TIME_INTERVAL = 15000;
30
+
31
+/**
32
+ * Type of message sent from main thread to worker that contains init information:
33
+ * such as models directory and window screen size.
34
+ */
35
+export const INIT_WORKER = 'INIT_WORKER';
36
+
37
+
38
+/**
39
+ * Type of message sent from main thread to worker that contain image data and
40
+ * will set a timeout for sending back the expression if detected in the worker.
41
+ */
42
+export const SET_TIMEOUT = 'SET_TIMEOUT';
43
+
44
+/**
45
+ * Type of message sent from main thread to worker that will stop the recognition;
46
+ * the worker will clear the timeout and then will send nothing back.
47
+ */
48
+export const CLEAR_TIMEOUT = 'CLEAR_TIMEOUT';
49
+
50
+/**
51
+ * Type of message sent from the worker to main thread that contains a facial expression or undefined.
52
+ */
53
+export const FACIAL_EXPRESSION_MESSAGE = 'FACIAL_EXPRESSION_MESSAGE_TYPE';
54
+
55
+/**
56
+ * Type of message sent from the worker to main thread that contains the time interval chosen by the worker.
57
+ */
58
+export const INTERVAL_MESSAGE = 'INTERVAL_MESSAGE_TYPE';

+ 29
- 20
react/features/facial-recognition/facialExpressionsWorker.js View File

@@ -2,6 +2,16 @@
2 2
 import './faceApiPatch';
3 3
 import * as faceapi from 'face-api.js';
4 4
 
5
+import {
6
+    CLEAR_TIMEOUT,
7
+    CPU_TIME_INTERVAL,
8
+    FACIAL_EXPRESSION_MESSAGE,
9
+    INIT_WORKER,
10
+    SET_TIMEOUT,
11
+    INTERVAL_MESSAGE,
12
+    WEBGL_TIME_INTERVAL
13
+} from './constants';
14
+
5 15
 /**
6 16
  * A flag that indicates whether the tensorflow models were loaded or not.
7 17
  */
@@ -28,34 +38,29 @@ let timer;
28 38
 let timeoutDuration = -1;
29 39
 
30 40
 /**
31
- * Time used for detection interval when facial expressions worker uses webgl backend.
41
+ * A patch for having window object in the worker.
32 42
  */
33
-const WEBGL_TIME_INTERVAL = 1000;
34
-
35
-/**
36
- * Time used for detection interval when facial expression worker uses cpu backend.
37
- */
38
-const CPU_TIME_INTERVAL = 6000;
39
-
40
-// eslint-disable-next-line no-unused-vars
41 43
 const window = {
42 44
     screen: {
43 45
         width: 1280,
44 46
         height: 720
45 47
     }
46
-
47 48
 };
48 49
 
49 50
 onmessage = async function(message) {
50
-    if (message.data.id === 'SET_MODELS_URL') {
51
+    switch (message.data.type) {
52
+    case INIT_WORKER : {
51 53
         modelsURL = message.data.url;
54
+        if (message.data.windowScreenSize) {
55
+            window.screen = message.data.windowScreenSize;
56
+        }
57
+        break;
52 58
     }
53 59
 
54
-    // Receives image data
55
-    if (message.data.id === 'SET_TIMEOUT') {
60
+    case SET_TIMEOUT : {
56 61
         if (!message.data.imageData || !modelsURL) {
57 62
             self.postMessage({
58
-                type: 'facial-expression',
63
+                type: FACIAL_EXPRESSION_MESSAGE,
59 64
                 value: null
60 65
             });
61 66
         }
@@ -77,15 +82,15 @@ onmessage = async function(message) {
77 82
         if (!backendSet) {
78 83
             const backend = faceapi.tf.getBackend();
79 84
 
80
-            if (backend !== undefined) {
85
+            if (backend) {
81 86
                 if (backend === 'webgl') {
82 87
                     timeoutDuration = WEBGL_TIME_INTERVAL;
83 88
                 } else if (backend === 'cpu') {
84 89
                     timeoutDuration = CPU_TIME_INTERVAL;
85 90
                 }
86 91
                 self.postMessage({
87
-                    type: 'tf-backend',
88
-                    value: backend
92
+                    type: INTERVAL_MESSAGE,
93
+                    value: timeoutDuration
89 94
                 });
90 95
                 backendSet = true;
91 96
             }
@@ -98,15 +103,19 @@ onmessage = async function(message) {
98 103
         }
99 104
         timer = setTimeout(() => {
100 105
             self.postMessage({
101
-                type: 'facial-expression',
106
+                type: FACIAL_EXPRESSION_MESSAGE,
102 107
                 value: facialExpression
103 108
             });
104 109
         }, timeoutDuration);
105
-    } else if (message.data.id === 'CLEAR_TIMEOUT') {
106
-        // Clear the timeout.
110
+        break;
111
+    }
112
+
113
+    case CLEAR_TIMEOUT: {
107 114
         if (timer) {
108 115
             clearTimeout(timer);
109 116
             timer = null;
110 117
         }
118
+        break;
119
+    }
111 120
     }
112 121
 };

+ 2
- 2
react/features/facial-recognition/functions.js View File

@@ -2,6 +2,7 @@
2 2
 import { getLocalParticipant } from '../base/participants';
3 3
 import { extractFqnFromPath } from '../dynamic-branding';
4 4
 
5
+import { SET_TIMEOUT } from './constants';
5 6
 import logger from './logger';
6 7
 
7 8
 /**
@@ -120,7 +121,6 @@ export async function sendDataToWorker(
120 121
     if (imageCapture === null || imageCapture === undefined) {
121 122
         return;
122 123
     }
123
-
124 124
     let imageBitmap;
125 125
 
126 126
     try {
@@ -141,7 +141,7 @@ export async function sendDataToWorker(
141 141
     const imageData = context.getImageData(0, 0, imageBitmap.width, imageBitmap.height);
142 142
 
143 143
     worker.postMessage({
144
-        id: 'SET_TIMEOUT',
144
+        type: SET_TIMEOUT,
145 145
         imageData
146 146
     });
147 147
 }

Loading…
Cancel
Save