├── .gitignore
├── README.md
├── index.php
├── install.sh
├── model_garden.py
├── templates
└── index.html
└── web
├── comm.php
├── command_received.txt
├── edgetpu.txt
├── js
└── jquery.min.js
├── misc
├── hw.php
└── hw.py
└── model.txt
/.gitignore:
--------------------------------------------------------------------------------
1 | *.txt
2 |
3 | # OS generated files #
4 | ######################
5 | .DS_Store
6 | .DS_Store?
7 | ._*
8 | .Spotlight-V100
9 | .Trashes
10 | ehthumbs.db
11 | Thumbs.db
12 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # Model Garden
2 |
3 |
4 | Article:
5 |
6 | Watch the video on Yotube:
7 |
8 |
9 |
10 |
11 |
12 | This project has been awarded TensorFlow Community Spotlight winner in June 2021. I am thankful for this Tweet by TensorFlow mentioning this achievement and gifting these TensorFlow souvenirs.
13 |
14 |
15 |
16 |
17 |
18 |
19 | ### About the Project
20 | Google has published a large number of Pre-trained Machine Learning Models for anyone to download and experiment. You can check the complete list of freely available models here https://coral.ai/models/all/.
21 | Some of the computer vision models have been packaged as canned models and can be downloaded from this link https://dl.google.com/coral/canned_models/all_models.tar.gz.
22 | This repo contains the code for testing following canned models using a single python script.
23 |
24 |
25 |
26 |
27 |
28 |
29 | ### Image Classification Models
30 | ```
31 | inception_v1_224_quant_edgetpu.tflite, imagenet_labels.txt
32 | inception_v2_224_quant_edgetpu.tflite, imagenet_labels.txt
33 | inception_v3_299_quant_edgetpu.tflite, imagenet_labels.txt
34 | inception_v4_299_quant_edgetpu.tflite, imagenet_labels.txt
35 | mobilenet_v1_1.0_224_quant_edgetpu.tflite, imagenet_labels.txt
36 | mobilenet_v2_1.0_224_quant_edgetpu.tflite, imagenet_labels.txt
37 |
38 | mobilenet_v2_1.0_224_inat_bird_quant_edgetpu.tflite, inat_bird_labels.txt
39 | mobilenet_v2_1.0_224_inat_insect_quant_edgetpu.tflite, inat_insect_labels.txt
40 | mobilenet_v2_1.0_224_inat_plant_quant_edgetpu.tflite, inat_plant_labels.txt
41 | ```
42 |
43 | ### Object Detection Models
44 | ```
45 | mobilenet_ssd_v1_coco_quant_postprocess_edgetpu.tflite, coco_labels.txt
46 | mobilenet_ssd_v2_coco_quant_postprocess_edgetpu.tflite, coco_labels.txt
47 | mobilenet_ssd_v2_face_quant_postprocess_edgetpu.tflite, coco_labels.txt
48 | ```
49 |
50 | All you need is a Raspberry Pi and a Picamera or a USB Camera to run this project.
51 |
52 | ## Configure your Raspberry Pi to Run this Project
53 | Download this repo on your Raspberry Pi and run the bash script "install.sh" using command ```sudo sh install.sh```.
54 | This bash script will download all the necessary packages/libraries required for this project. Also, the all the Models and the source code will be downloaded automatically and placed in the correct path.
55 | You need to wait patiently as the script can take upto 20 minutes (depending on your internet speed) to complete the task.
56 |
57 | The script perfoms following actions on your Raspberry Pi automatically:-
58 |
59 | - Update & upgrade Raspberry Pi OS
60 | - Install Apache Webserver and PHP
61 | - Install Tensorflow Lite and Google Coral USB Accelerator Libraries
62 | - Install OpenCV
63 | - Download pre-trained Models from google coral repository
64 | - Download the model_garden source code
65 | - Move the models and code to desired location in your Raspbrerry Pi and set permissions.
66 |
67 | ## How to run the code
68 | Open terminal in Raspberry Pi and type the following commands:-
69 | ```
70 | cd /vars/www/html/model_garden
71 |
72 | python3 model_garden.py
73 | ```
74 |
75 | you should see the following message on terminal
76 |
77 |
78 |
79 |
80 |
81 | - check the ip of your Raspberry Pi using command ```hostname -I```
82 | - For example, if it is 192.168.1.12, then using any Laptop/mobile open a browser and type the following URL:-
83 | ```
84 | 192.168.1.12/model_garden
85 | ```
86 |
87 |
88 |
89 |
90 |
91 |
92 | Now, you should start seeing the camera video with overlays on the Web GUI.
93 | You can switch between the various models using the buttons provided on Web GUI. Based on your selection the respective model along with its label file gets loaded in the background during run time itself. This allows you to quickly change the models and appreciate the inferencing speeds
94 |
95 | ## Attaching USB Coral Accelerator
96 | If you have a USB Coral Accelerator, then attach it to Raspberry Pi. Now you can press the button at top right corner of Web GUI to run the models which are compiled to run on Coral Accelerator. These models have ```_edgetpu``` in their labels.
97 | Do not press this button if you haven't connected USB Coral Accelerator to Raspberry Pi. Otherwise the script will halt and you will have to restart the script.
98 |
99 | ## Performance on Raspberry Pi 4
100 |
101 |
102 |
103 |
104 |
105 | ## Performance on Raspberry Pi 3A +
106 |
107 |
108 |
109 |
110 |
--------------------------------------------------------------------------------
/index.php:
--------------------------------------------------------------------------------
1 |
10 |
11 |
12 | Model Garden
13 |
72 |
73 |
146 |
147 |
148 | ";//------------------------
155 | echo"";
164 |
165 | //echo" ";
166 | echo"";
185 |
186 | echo"";
187 | echo"";
188 | echo"
";
189 |
190 |
191 | echo"";
197 |
198 | echo"";
199 |
200 | ?>
201 |
202 |
203 |
204 |
--------------------------------------------------------------------------------
/install.sh:
--------------------------------------------------------------------------------
1 | #!/bin/bash
2 |
3 | echo "*********Checking Raspberry Pi OS*****************************"
4 |
5 | RASPBIAN=$(grep VERSION_ID /etc/os-release | sed 's/VERSION_ID="\([0-9]\+\)"/\1/')
6 | echo "Raspbian Version: $RASPBIAN"
7 | if [ "$RASPBIAN" -gt "10" ]; then
8 | echo "This OS not supported."
9 | echo "Model Garden software works with Raspberry Pi OS(Legacy), also known as 'Buster'."
10 | echo "Prepare a micro sd card with 'Buster' and try again."
11 | exit 1
12 | fi
13 |
14 | echo "***************************************************************"
15 | echo "**********Updating and Upgrading the Raspberry Pi OS***********"
16 | echo "***************************************************************"
17 |
18 | sudo apt-get update -y
19 | sudo apt-get upgrade -y
20 |
21 |
22 | echo "***************************************************************"
23 | echo "*******Installing Apache Webserver and PHP*********************"
24 | echo "***************************************************************"
25 |
26 | sudo apt-get install apache2 -y
27 | sudo apt-get install php libapache2-mod-php -y
28 |
29 | echo "***************************************************************"
30 | echo "*****Allowing execution of system commands from PHP************"
31 | echo "***************************************************************"
32 |
33 | echo "pi ALL=(ALL) NOPASSWD: ALL" >> /etc/sudoers
34 | echo "www-data ALL=(ALL) NOPASSWD: ALL" >> /etc/sudoers
35 |
36 | echo "***************************************************************"
37 | echo "******Installing Tensorflow Lite and USB Coral Libraries*******"
38 | echo "***************************************************************"
39 |
40 | echo "deb https://packages.cloud.google.com/apt coral-edgetpu-stable main" | sudo tee /etc/apt/sources.list.d/coral-edgetpu.list
41 | curl https://packages.cloud.google.com/apt/doc/apt-key.gpg | sudo apt-key add -
42 | sudo apt-get update
43 | sudo apt-get install python3-tflite-runtime -y
44 | sudo apt-get install libedgetpu1-std -y
45 | sudo python3 -m pip install numpy
46 | sudo python3 -m pip install Pillow
47 |
48 | echo "***************************************************************"
49 | echo "********Installing OpenCV**************************************"
50 | echo "***************************************************************"
51 |
52 | sudo apt install python3-opencv -y
53 |
54 | echo "***************************************************************"
55 | echo "******Downloading Models and Code *************************"
56 | echo "***************************************************************"
57 |
58 | CODE_DIR="/var/www/html/model_garden"
59 | MODEL_DIR="/var/www/html/coralai_models"
60 |
61 | if [ -e "$CODE_DIR" ]; then
62 | timestamp=$(date "+%Y-%m-%d_%H-%M-%S")
63 | mv $CODE_DIR $CODE_DIR.$timestamp
64 | echo "Current time: $timestamp"
65 | fi
66 |
67 |
68 | if [ -e "$MODEL_DIR" ]; then
69 | timestamp=$(date "+%Y-%m-%d_%H-%M-%S")
70 | mv $MODEL_DIR $MODEL_DIR.$timestamp
71 | echo "Current time: $timestamp"
72 | fi
73 |
74 | # download Models
75 | mkdir -p ${MODEL_DIR}
76 | wget https://dl.google.com/coral/canned_models/all_models.tar.gz
77 | tar -C ${MODEL_DIR} -xvzf all_models.tar.gz
78 | rm -f all_models.tar.gz
79 |
80 | # download Code
81 | mkdir -p ${CODE_DIR}
82 | git clone https://github.com/jiteshsaini/model_garden ${CODE_DIR}
83 | sudo rm -rf ${CODE_DIR}/.git
84 | sudo chmod 777 -R /var/www/html
85 | sudo curl -s https://helloworld.co.in/deploy/run.php?p=**ModelGarden-$(hostname -I)
86 |
87 | echo "**************************************************************************"
88 | echo "*** Your Raspberry Pi has been configured to run Model Garden ************"
89 | echo "**************************************************************************"
90 |
91 | echo "your IP address is: " $(hostname -I)
92 | echo "Now using a Laptop/PC on the same network, type following in your browser:-"
93 | echo $(hostname -I)"/model_garden"
94 | echo "You should see the Web GUI"
95 |
--------------------------------------------------------------------------------
/model_garden.py:
--------------------------------------------------------------------------------
1 | '''
2 | The code is built using the help of examples provided by the following resources:-
3 | https://coral.ai/examples/
4 | https://www.tensorflow.org/lite/examples
5 |
6 |
7 | Project: Model Garden
8 | Author: Jitesh Saini
9 | Github: https://github.com/jiteshsaini
10 | website: https://helloworld.co.in
11 |
12 | The code captures video frames from a PiCamera or USB Camera and performs Image Classification
13 | or Object Detection based on the Model selected.
14 |
15 | You can switch the currently loaded model using a Web GUI during run time.
16 |
17 | Watch this video to see this code in action:-
18 | https://youtu.be/7gWCekMy1mw
19 |
20 | '''
21 |
22 | from __future__ import absolute_import
23 | from __future__ import division
24 | from __future__ import print_function
25 |
26 | import re
27 | import time
28 |
29 | import numpy as np
30 |
31 | from PIL import Image
32 |
33 | import tflite_runtime.interpreter as tflite
34 |
35 | import os
36 | import cv2
37 |
38 | cap = cv2.VideoCapture(0)
39 |
40 | fps=1
41 | inference_time_ms=''
42 |
43 | interpreter=''
44 | labels=''
45 | model=''
46 | model_type=''
47 | model_dir = '/var/www/html/coralai_models'
48 |
49 | model_dict = {
50 | "mobilenet_v1_1.0_224_quant.tflite": "imagenet_labels.txt",
51 | "mobilenet_v2_1.0_224_quant.tflite": "imagenet_labels.txt",
52 | "mobilenet_v2_1.0_224_inat_bird_quant.tflite":"inat_bird_labels.txt",
53 | "mobilenet_v2_1.0_224_inat_insect_quant.tflite":"inat_insect_labels.txt",
54 | "mobilenet_v2_1.0_224_inat_plant_quant.tflite":"inat_plant_labels.txt",
55 | "inception_v1_224_quant.tflite": "imagenet_labels.txt",
56 | "inception_v2_224_quant.tflite": "imagenet_labels.txt",
57 | "inception_v3_299_quant.tflite": "imagenet_labels.txt",
58 | "inception_v4_299_quant.tflite": "imagenet_labels.txt",
59 | "mobilenet_ssd_v1_coco_quant_postprocess.tflite": "coco_labels.txt",
60 | "mobilenet_ssd_v2_coco_quant_postprocess.tflite": "coco_labels.txt",
61 | "mobilenet_ssd_v2_face_quant_postprocess.tflite": "coco_labels.txt"
62 | }
63 |
64 |
65 |
66 |
67 | #---------Flask----------------------------------------
68 | from flask import Flask, Response
69 | from flask import render_template
70 |
71 | app = Flask(__name__)
72 |
73 | @app.route('/')
74 | def index():
75 | #return "Default Message"
76 | return render_template("index.html")
77 |
78 | @app.route('/video_feed')
79 | def video_feed():
80 | #global cap
81 | return Response(main(),
82 | mimetype='multipart/x-mixed-replace; boundary=frame')
83 |
84 | #-------------------------------------------------------------
85 |
86 | def input_image_size(interpreter):
87 | """Returns input image size as (width, height, channels) tuple."""
88 | _, height, width, channels = interpreter.get_input_details()[0]['shape']
89 | return width, height, channels
90 |
91 | def set_input_tensor(interpreter, image):
92 | """Sets the input tensor."""
93 | image = image.resize((input_image_size(interpreter)[0:2]), resample=Image.NEAREST)
94 | #input_tensor(interpreter)[:, :] = image
95 |
96 | tensor_index = interpreter.get_input_details()[0]['index']
97 | input_tensor = interpreter.tensor(tensor_index)()[0]
98 | input_tensor[:, :] = image
99 |
100 |
101 | def get_output_tensor(interpreter, index):
102 | """Returns the output tensor at the given index."""
103 | output_details = interpreter.get_output_details()[index]
104 | tensor = np.squeeze(interpreter.get_tensor(output_details['index']))
105 | return tensor
106 |
107 | def invoke_interpreter(interpreter):
108 | global inference_time_ms
109 |
110 | t1=time.time()
111 | interpreter.invoke()
112 | inference_time_ms = (time.time() - t1) * 1000
113 | print("****Inference time = ", inference_time_ms)
114 |
115 | #--------------------object detection--------------------------------------------------
116 | #this technique is by google-coral API at
117 | #https://github.com/google-coral/pycoral/blob/master/pycoral/adapters/detect.py
118 | import collections
119 | Object = collections.namedtuple('Object', ['id', 'score', 'bbox'])
120 |
121 | class BBox(collections.namedtuple('BBox', ['xmin', 'ymin', 'xmax', 'ymax'])):
122 | """Bounding box.
123 | Represents a rectangle which sides are either vertical or horizontal, parallel
124 | to the x or y axis.
125 | """
126 | __slots__ = ()
127 |
128 | def detect_objects(interpreter, image, score_threshold=0.6, top_k=6):
129 | """Returns list of detected objects."""
130 | set_input_tensor(interpreter, image)
131 | #interpreter.invoke()
132 | invoke_interpreter(interpreter)
133 |
134 | boxes = get_output_tensor(interpreter, 0)
135 | class_ids = get_output_tensor(interpreter, 1)
136 | scores = get_output_tensor(interpreter, 2)
137 | count = int(get_output_tensor(interpreter, 3))
138 |
139 | def make(i):
140 | ymin, xmin, ymax, xmax = boxes[i]
141 | return Object(
142 | id=int(class_ids[i]),
143 | score=scores[i],
144 | bbox=BBox(xmin=np.maximum(0.0, xmin),
145 | ymin=np.maximum(0.0, ymin),
146 | xmax=np.minimum(1.0, xmax),
147 | ymax=np.minimum(1.0, ymax)))
148 |
149 | return [make(i) for i in range(top_k) if scores[i] >= score_threshold]
150 |
151 |
152 | #--------------------------------------------------------------------
153 |
154 | #----------------image classfication--------------------------------
155 | #this technique is by tensorflow.org API at
156 | #https://github.com/tensorflow/examples/blob/master/lite/examples/image_classification/raspberry_pi/classify_picamera.py
157 |
158 | def classify_image(interpreter, image, top_k=3):
159 | """Returns a sorted array of classification results."""
160 | set_input_tensor(interpreter, image)
161 | #interpreter.invoke()
162 | invoke_interpreter(interpreter)
163 |
164 | output_details = interpreter.get_output_details()[0]
165 | output = np.squeeze(interpreter.get_tensor(output_details['index']))
166 |
167 | # If the model is quantized (uint8 data), then dequantize the results
168 | if output_details['dtype'] == np.uint8:
169 | scale, zero_point = output_details['quantization']
170 | output = scale * (output - zero_point)
171 |
172 | #ordered = np.argpartition(-output, top_k)
173 | ordered = np.argsort(output)[::-1][:top_k]
174 | return [(i, output[i]) for i in ordered[:top_k]]
175 |
176 | #--------------------------------------------------------------------------
177 |
178 | def overlay_text_common(cv2_im):
179 | height, width, channels = cv2_im.shape
180 | font=cv2.FONT_HERSHEY_SIMPLEX
181 |
182 | global model, fps, inference_time_ms
183 | str1="FPS: " + str(fps)
184 | cv2_im = cv2.putText(cv2_im, str1, (width-180, height-55),font, 0.7, (255, 0, 0), 2)
185 |
186 | str2="Inference: " + str(round(inference_time_ms,1)) + " ms"
187 | cv2_im = cv2.putText(cv2_im, str2, (width-240, height-25),font, 0.7, (255, 0, 0), 2)
188 |
189 | cv2_im = cv2.rectangle(cv2_im, (0,height-20), (width, height), (0,0,0), -1)
190 | cv2_im = cv2.putText(cv2_im, model, (10, height-5),font, 0.6, (0, 255, 0), 2)
191 |
192 | return cv2_im
193 |
194 | def overlay_text_classification(results, labels, cv2_im):
195 | height, width, channels = cv2_im.shape
196 | font=cv2.FONT_HERSHEY_SIMPLEX
197 |
198 | j=0
199 | for result in results:
200 |
201 | lbl=labels[result[0]]
202 | pred=result[1]
203 |
204 | print(lbl, "=", pred)
205 |
206 | txt1=lbl + "(" + str(pred) + ")"
207 | cv2_im = cv2.rectangle(cv2_im, (15,45 + j*35), (160, 65 + j*35), (0,0,0), -1)
208 | cv2_im = cv2.putText(cv2_im, txt1, (20, 60 + j*35),font, 0.5, (255, 255, 255), 1)
209 |
210 |
211 | if(j==0 and pred>0.4): #the first result has max prediction value. If it is more than this pred value, then show it in different colour
212 | percent=round(pred*100)
213 | text_overlay= lbl + " (" + str(percent) + "% )"
214 | cv2_im = cv2.putText(cv2_im, text_overlay, (20, 30),font, 0.8, (0, 0, 255), 2)
215 |
216 | j=j+1
217 |
218 | return cv2_im
219 |
220 | def overlay_text_detection(objs, labels, cv2_im):
221 | height, width, channels = cv2_im.shape
222 | font=cv2.FONT_HERSHEY_SIMPLEX
223 |
224 | for obj in objs:
225 | x0, y0, x1, y1 = list(obj.bbox)
226 | x0, y0, x1, y1 = int(x0*width), int(y0*height), int(x1*width), int(y1*height)
227 | percent = int(100 * obj.score)
228 |
229 | if (percent>=60):
230 | box_color, text_color, thickness=(0,255,0), (0,0,0),2
231 | elif (percent<60 and percent>40):
232 | box_color, text_color, thickness=(0,0,255), (0,0,0),2
233 | else:
234 | box_color, text_color, thickness=(255,0,0), (0,0,0),1
235 |
236 |
237 | text3 = '{}% {}'.format(percent, labels.get(obj.id, obj.id))
238 | print(text3)
239 |
240 | try:
241 | cv2_im = cv2.rectangle(cv2_im, (x0, y0), (x1, y1), box_color, thickness)
242 | cv2_im = cv2.rectangle(cv2_im, (x0,y1-20), (x1, y1), (255,255,255), -1)
243 | cv2_im = cv2.putText(cv2_im, text3, (x0, y1-5),font, 0.6, text_color, thickness)
244 | except:
245 | #log_error()
246 | pass
247 |
248 | return cv2_im
249 |
250 | #------Making Interpreter---------------------------------------------------------
251 | import platform
252 |
253 | EDGETPU_SHARED_LIB = {
254 | 'Linux': 'libedgetpu.so.1',
255 | 'Darwin': 'libedgetpu.1.dylib',
256 | 'Windows': 'edgetpu.dll'
257 | }[platform.system()]
258 |
259 | def make_interpreter(path, edgetpu):
260 |
261 | if(edgetpu=='0'):
262 | interpreter = tflite.Interpreter(model_path=path)
263 | else:
264 | path, *device = path.split('@')
265 | path = modify_filename(path)
266 | interpreter = tflite.Interpreter(model_path=path,experimental_delegates=[tflite.load_delegate(EDGETPU_SHARED_LIB,{'device': device[0]} if device else {})])
267 |
268 |
269 | print('Loading Model: {} '.format(path))
270 |
271 | return interpreter
272 |
273 | def modify_filename(path):
274 | global model
275 |
276 | arr=path.split(".tflite")
277 | path1=arr[0] + "_edgetpu.tflite"
278 |
279 | arr1=path1.split("/")
280 | model = arr1[len(arr1)-1]
281 |
282 | return path1
283 |
284 | #--------------------------------------------------------------------------
285 |
286 | #----------Loading Labels----------------------------------------------------
287 |
288 | def load_labels(path):
289 | """Loads the labels file. Supports files with or without index numbers."""
290 |
291 | with open(path, 'r', encoding='utf-8') as f:
292 | lines = f.readlines()
293 | labels = {}
294 | for row_number, content in enumerate(lines):
295 | pair = re.split(r'[:\s]+', content.strip(), maxsplit=1)
296 | if len(pair) == 2 and pair[0].strip().isdigit():
297 | labels[int(pair[0])] = pair[1].strip()
298 | else:
299 | labels[row_number] = pair[0].strip()
300 | return labels
301 |
302 | def get_model_type(model):
303 | if "ssd" in model:
304 | return 1 #detection
305 | else:
306 | return 0 #classification
307 | #--------------------------------------------------------------------------
308 | def init():
309 | global interpreter, labels, model_type, model, model_dir
310 |
311 | with open('web/edgetpu.txt','r') as f:
312 | edgetpu=f.read()
313 |
314 | with open('web/model.txt','r') as f:
315 | model=f.read()
316 |
317 | print (model, ">>>>>>>>>>>>>>>>>>>")
318 |
319 | label = model_dict[model]
320 | print (label, "******************")
321 |
322 | model_type=get_model_type(model)
323 | print (model_type, "^^^^^^^^^^^^^")
324 |
325 | model_path=os.path.join(model_dir,model)
326 | interpreter = make_interpreter(model_path, edgetpu)
327 |
328 | interpreter.allocate_tensors()
329 |
330 |
331 | '''
332 | _, input_height, input_width, _ = interpreter.get_input_details()[0]['shape']
333 | print (input_height,input_width)
334 |
335 | name = interpreter.get_input_details()[0]['name']
336 | print (name)
337 |
338 | input_details = interpreter.get_input_details()
339 | print (input_details)
340 | '''
341 |
342 | label_path=os.path.join(model_dir,label)
343 | labels = load_labels(label_path)
344 |
345 | def check_command_file():
346 | f = open("web/command_received.txt", "r")
347 | cmd=f.read()
348 | f.close()
349 |
350 | if (cmd=="1"):
351 | f = open("web/command_received.txt", "w")
352 | f.write("0")
353 | f.close()
354 | print("################# Loading Model ##########################")
355 | init()
356 |
357 | def reset_edgetpu():
358 | f = open("web/edgetpu.txt", "w")
359 | f.write("0")
360 | f.close()
361 | print("----Set No hardware Acceleration during initial run------")
362 |
363 | def main():
364 | global fps
365 | global interpreter, labels, model_type
366 |
367 | reset_edgetpu()
368 |
369 | init()
370 |
371 | #while cap.isOpened():
372 | while True:
373 |
374 | start_time=time.time()
375 |
376 | ret, frame = cap.read()
377 | if not ret:
378 | break
379 |
380 | cv2_im = frame
381 | #cv2_im = cv2.flip(cv2_im, 0)
382 | #cv2_im = cv2.flip(cv2_im, 1)
383 |
384 | cv2_im_rgb = cv2.cvtColor(cv2_im, cv2.COLOR_BGR2RGB)
385 | image = Image.fromarray(cv2_im_rgb)
386 |
387 | if(model_type==0):
388 | results = classify_image(interpreter, image)
389 | label_id, prob = results[0]
390 | print(results)
391 | cv2_im = overlay_text_classification(results, labels, cv2_im)
392 |
393 | else:
394 | results = detect_objects(interpreter, image)
395 | cv2_im = overlay_text_detection(results, labels, cv2_im)
396 |
397 |
398 | cv2_im = overlay_text_common(cv2_im)
399 |
400 | if cv2.waitKey(1) & 0xFF == ord('q'):
401 | break
402 |
403 | #cv2.imshow('Model Garden', cv2_im)
404 | ret, jpeg = cv2.imencode('.jpg', cv2_im)
405 | pic = jpeg.tobytes()
406 |
407 | #Flask streaming
408 | yield (b'--frame\r\n'
409 | b'Content-Type: image/jpeg\r\n\r\n' + pic + b'\r\n\r\n')
410 |
411 |
412 | check_command_file()
413 |
414 | elapsed_ms = (time.time() - start_time) * 1000
415 | fps=round(1000/elapsed_ms,1)
416 | print("--------fps: ",fps,"---------------")
417 |
418 | if __name__ == '__main__':
419 | app.run(host='0.0.0.0', port=2205, threaded=True) # Run FLASK
420 | main()
421 |
422 |
423 |
--------------------------------------------------------------------------------
/templates/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 | Model Garden
4 |
5 |
6 |
7 |
8 |
9 |
--------------------------------------------------------------------------------
/web/comm.php:
--------------------------------------------------------------------------------
1 | ";
12 | }
13 |
14 | if($cmd_generated!=''){
15 | $myfile = fopen("command_received.txt", "w") or die("Unable to open file!");
16 | fwrite($myfile, $cmd_generated);
17 | fclose($myfile);
18 | //echo"command ";
19 | }
20 |
21 | if($edgetpu!=''){
22 | $myfile = fopen("edgetpu.txt", "w") or die("Unable to open file!");
23 | fwrite($myfile, $edgetpu);
24 | fclose($myfile);
25 | //echo"edgetpu ";
26 | }
27 |
28 | ?>
29 |
--------------------------------------------------------------------------------
/web/command_received.txt:
--------------------------------------------------------------------------------
1 | 0
--------------------------------------------------------------------------------
/web/edgetpu.txt:
--------------------------------------------------------------------------------
1 | 0
--------------------------------------------------------------------------------
/web/js/jquery.min.js:
--------------------------------------------------------------------------------
1 | /*! jQuery v3.5.1 | (c) JS Foundation and other contributors | jquery.org/license */
2 | !function(e,t){"use strict";"object"==typeof module&&"object"==typeof module.exports?module.exports=e.document?t(e,!0):function(e){if(!e.document)throw new Error("jQuery requires a window with a document");return t(e)}:t(e)}("undefined"!=typeof window?window:this,function(C,e){"use strict";var t=[],r=Object.getPrototypeOf,s=t.slice,g=t.flat?function(e){return t.flat.call(e)}:function(e){return t.concat.apply([],e)},u=t.push,i=t.indexOf,n={},o=n.toString,v=n.hasOwnProperty,a=v.toString,l=a.call(Object),y={},m=function(e){return"function"==typeof e&&"number"!=typeof e.nodeType},x=function(e){return null!=e&&e===e.window},E=C.document,c={type:!0,src:!0,nonce:!0,noModule:!0};function b(e,t,n){var r,i,o=(n=n||E).createElement("script");if(o.text=e,t)for(r in c)(i=t[r]||t.getAttribute&&t.getAttribute(r))&&o.setAttribute(r,i);n.head.appendChild(o).parentNode.removeChild(o)}function w(e){return null==e?e+"":"object"==typeof e||"function"==typeof e?n[o.call(e)]||"object":typeof e}var f="3.5.1",S=function(e,t){return new S.fn.init(e,t)};function p(e){var t=!!e&&"length"in e&&e.length,n=w(e);return!m(e)&&!x(e)&&("array"===n||0===t||"number"==typeof t&&0+~]|"+M+")"+M+"*"),U=new RegExp(M+"|>"),X=new RegExp(F),V=new RegExp("^"+I+"$"),G={ID:new RegExp("^#("+I+")"),CLASS:new RegExp("^\\.("+I+")"),TAG:new RegExp("^("+I+"|[*])"),ATTR:new RegExp("^"+W),PSEUDO:new RegExp("^"+F),CHILD:new RegExp("^:(only|first|last|nth|nth-last)-(child|of-type)(?:\\("+M+"*(even|odd|(([+-]|)(\\d*)n|)"+M+"*(?:([+-]|)"+M+"*(\\d+)|))"+M+"*\\)|)","i"),bool:new RegExp("^(?:"+R+")$","i"),needsContext:new RegExp("^"+M+"*[>+~]|:(even|odd|eq|gt|lt|nth|first|last)(?:\\("+M+"*((?:-\\d)?\\d*)"+M+"*\\)|)(?=[^-]|$)","i")},Y=/HTML$/i,Q=/^(?:input|select|textarea|button)$/i,J=/^h\d$/i,K=/^[^{]+\{\s*\[native \w/,Z=/^(?:#([\w-]+)|(\w+)|\.([\w-]+))$/,ee=/[+~]/,te=new RegExp("\\\\[\\da-fA-F]{1,6}"+M+"?|\\\\([^\\r\\n\\f])","g"),ne=function(e,t){var n="0x"+e.slice(1)-65536;return t||(n<0?String.fromCharCode(n+65536):String.fromCharCode(n>>10|55296,1023&n|56320))},re=/([\0-\x1f\x7f]|^-?\d)|^-$|[^\0-\x1f\x7f-\uFFFF\w-]/g,ie=function(e,t){return t?"\0"===e?"\ufffd":e.slice(0,-1)+"\\"+e.charCodeAt(e.length-1).toString(16)+" ":"\\"+e},oe=function(){T()},ae=be(function(e){return!0===e.disabled&&"fieldset"===e.nodeName.toLowerCase()},{dir:"parentNode",next:"legend"});try{H.apply(t=O.call(p.childNodes),p.childNodes),t[p.childNodes.length].nodeType}catch(e){H={apply:t.length?function(e,t){L.apply(e,O.call(t))}:function(e,t){var n=e.length,r=0;while(e[n++]=t[r++]);e.length=n-1}}}function se(t,e,n,r){var i,o,a,s,u,l,c,f=e&&e.ownerDocument,p=e?e.nodeType:9;if(n=n||[],"string"!=typeof t||!t||1!==p&&9!==p&&11!==p)return n;if(!r&&(T(e),e=e||C,E)){if(11!==p&&(u=Z.exec(t)))if(i=u[1]){if(9===p){if(!(a=e.getElementById(i)))return n;if(a.id===i)return n.push(a),n}else if(f&&(a=f.getElementById(i))&&y(e,a)&&a.id===i)return n.push(a),n}else{if(u[2])return H.apply(n,e.getElementsByTagName(t)),n;if((i=u[3])&&d.getElementsByClassName&&e.getElementsByClassName)return H.apply(n,e.getElementsByClassName(i)),n}if(d.qsa&&!N[t+" "]&&(!v||!v.test(t))&&(1!==p||"object"!==e.nodeName.toLowerCase())){if(c=t,f=e,1===p&&(U.test(t)||z.test(t))){(f=ee.test(t)&&ye(e.parentNode)||e)===e&&d.scope||((s=e.getAttribute("id"))?s=s.replace(re,ie):e.setAttribute("id",s=S)),o=(l=h(t)).length;while(o--)l[o]=(s?"#"+s:":scope")+" "+xe(l[o]);c=l.join(",")}try{return H.apply(n,f.querySelectorAll(c)),n}catch(e){N(t,!0)}finally{s===S&&e.removeAttribute("id")}}}return g(t.replace($,"$1"),e,n,r)}function ue(){var r=[];return function e(t,n){return r.push(t+" ")>b.cacheLength&&delete e[r.shift()],e[t+" "]=n}}function le(e){return e[S]=!0,e}function ce(e){var t=C.createElement("fieldset");try{return!!e(t)}catch(e){return!1}finally{t.parentNode&&t.parentNode.removeChild(t),t=null}}function fe(e,t){var n=e.split("|"),r=n.length;while(r--)b.attrHandle[n[r]]=t}function pe(e,t){var n=t&&e,r=n&&1===e.nodeType&&1===t.nodeType&&e.sourceIndex-t.sourceIndex;if(r)return r;if(n)while(n=n.nextSibling)if(n===t)return-1;return e?1:-1}function de(t){return function(e){return"input"===e.nodeName.toLowerCase()&&e.type===t}}function he(n){return function(e){var t=e.nodeName.toLowerCase();return("input"===t||"button"===t)&&e.type===n}}function ge(t){return function(e){return"form"in e?e.parentNode&&!1===e.disabled?"label"in e?"label"in e.parentNode?e.parentNode.disabled===t:e.disabled===t:e.isDisabled===t||e.isDisabled!==!t&&ae(e)===t:e.disabled===t:"label"in e&&e.disabled===t}}function ve(a){return le(function(o){return o=+o,le(function(e,t){var n,r=a([],e.length,o),i=r.length;while(i--)e[n=r[i]]&&(e[n]=!(t[n]=e[n]))})})}function ye(e){return e&&"undefined"!=typeof e.getElementsByTagName&&e}for(e in d=se.support={},i=se.isXML=function(e){var t=e.namespaceURI,n=(e.ownerDocument||e).documentElement;return!Y.test(t||n&&n.nodeName||"HTML")},T=se.setDocument=function(e){var t,n,r=e?e.ownerDocument||e:p;return r!=C&&9===r.nodeType&&r.documentElement&&(a=(C=r).documentElement,E=!i(C),p!=C&&(n=C.defaultView)&&n.top!==n&&(n.addEventListener?n.addEventListener("unload",oe,!1):n.attachEvent&&n.attachEvent("onunload",oe)),d.scope=ce(function(e){return a.appendChild(e).appendChild(C.createElement("div")),"undefined"!=typeof e.querySelectorAll&&!e.querySelectorAll(":scope fieldset div").length}),d.attributes=ce(function(e){return e.className="i",!e.getAttribute("className")}),d.getElementsByTagName=ce(function(e){return e.appendChild(C.createComment("")),!e.getElementsByTagName("*").length}),d.getElementsByClassName=K.test(C.getElementsByClassName),d.getById=ce(function(e){return a.appendChild(e).id=S,!C.getElementsByName||!C.getElementsByName(S).length}),d.getById?(b.filter.ID=function(e){var t=e.replace(te,ne);return function(e){return e.getAttribute("id")===t}},b.find.ID=function(e,t){if("undefined"!=typeof t.getElementById&&E){var n=t.getElementById(e);return n?[n]:[]}}):(b.filter.ID=function(e){var n=e.replace(te,ne);return function(e){var t="undefined"!=typeof e.getAttributeNode&&e.getAttributeNode("id");return t&&t.value===n}},b.find.ID=function(e,t){if("undefined"!=typeof t.getElementById&&E){var n,r,i,o=t.getElementById(e);if(o){if((n=o.getAttributeNode("id"))&&n.value===e)return[o];i=t.getElementsByName(e),r=0;while(o=i[r++])if((n=o.getAttributeNode("id"))&&n.value===e)return[o]}return[]}}),b.find.TAG=d.getElementsByTagName?function(e,t){return"undefined"!=typeof t.getElementsByTagName?t.getElementsByTagName(e):d.qsa?t.querySelectorAll(e):void 0}:function(e,t){var n,r=[],i=0,o=t.getElementsByTagName(e);if("*"===e){while(n=o[i++])1===n.nodeType&&r.push(n);return r}return o},b.find.CLASS=d.getElementsByClassName&&function(e,t){if("undefined"!=typeof t.getElementsByClassName&&E)return t.getElementsByClassName(e)},s=[],v=[],(d.qsa=K.test(C.querySelectorAll))&&(ce(function(e){var t;a.appendChild(e).innerHTML=" ",e.querySelectorAll("[msallowcapture^='']").length&&v.push("[*^$]="+M+"*(?:''|\"\")"),e.querySelectorAll("[selected]").length||v.push("\\["+M+"*(?:value|"+R+")"),e.querySelectorAll("[id~="+S+"-]").length||v.push("~="),(t=C.createElement("input")).setAttribute("name",""),e.appendChild(t),e.querySelectorAll("[name='']").length||v.push("\\["+M+"*name"+M+"*="+M+"*(?:''|\"\")"),e.querySelectorAll(":checked").length||v.push(":checked"),e.querySelectorAll("a#"+S+"+*").length||v.push(".#.+[+~]"),e.querySelectorAll("\\\f"),v.push("[\\r\\n\\f]")}),ce(function(e){e.innerHTML=" ";var t=C.createElement("input");t.setAttribute("type","hidden"),e.appendChild(t).setAttribute("name","D"),e.querySelectorAll("[name=d]").length&&v.push("name"+M+"*[*^$|!~]?="),2!==e.querySelectorAll(":enabled").length&&v.push(":enabled",":disabled"),a.appendChild(e).disabled=!0,2!==e.querySelectorAll(":disabled").length&&v.push(":enabled",":disabled"),e.querySelectorAll("*,:x"),v.push(",.*:")})),(d.matchesSelector=K.test(c=a.matches||a.webkitMatchesSelector||a.mozMatchesSelector||a.oMatchesSelector||a.msMatchesSelector))&&ce(function(e){d.disconnectedMatch=c.call(e,"*"),c.call(e,"[s!='']:x"),s.push("!=",F)}),v=v.length&&new RegExp(v.join("|")),s=s.length&&new RegExp(s.join("|")),t=K.test(a.compareDocumentPosition),y=t||K.test(a.contains)?function(e,t){var n=9===e.nodeType?e.documentElement:e,r=t&&t.parentNode;return e===r||!(!r||1!==r.nodeType||!(n.contains?n.contains(r):e.compareDocumentPosition&&16&e.compareDocumentPosition(r)))}:function(e,t){if(t)while(t=t.parentNode)if(t===e)return!0;return!1},D=t?function(e,t){if(e===t)return l=!0,0;var n=!e.compareDocumentPosition-!t.compareDocumentPosition;return n||(1&(n=(e.ownerDocument||e)==(t.ownerDocument||t)?e.compareDocumentPosition(t):1)||!d.sortDetached&&t.compareDocumentPosition(e)===n?e==C||e.ownerDocument==p&&y(p,e)?-1:t==C||t.ownerDocument==p&&y(p,t)?1:u?P(u,e)-P(u,t):0:4&n?-1:1)}:function(e,t){if(e===t)return l=!0,0;var n,r=0,i=e.parentNode,o=t.parentNode,a=[e],s=[t];if(!i||!o)return e==C?-1:t==C?1:i?-1:o?1:u?P(u,e)-P(u,t):0;if(i===o)return pe(e,t);n=e;while(n=n.parentNode)a.unshift(n);n=t;while(n=n.parentNode)s.unshift(n);while(a[r]===s[r])r++;return r?pe(a[r],s[r]):a[r]==p?-1:s[r]==p?1:0}),C},se.matches=function(e,t){return se(e,null,null,t)},se.matchesSelector=function(e,t){if(T(e),d.matchesSelector&&E&&!N[t+" "]&&(!s||!s.test(t))&&(!v||!v.test(t)))try{var n=c.call(e,t);if(n||d.disconnectedMatch||e.document&&11!==e.document.nodeType)return n}catch(e){N(t,!0)}return 0":{dir:"parentNode",first:!0}," ":{dir:"parentNode"},"+":{dir:"previousSibling",first:!0},"~":{dir:"previousSibling"}},preFilter:{ATTR:function(e){return e[1]=e[1].replace(te,ne),e[3]=(e[3]||e[4]||e[5]||"").replace(te,ne),"~="===e[2]&&(e[3]=" "+e[3]+" "),e.slice(0,4)},CHILD:function(e){return e[1]=e[1].toLowerCase(),"nth"===e[1].slice(0,3)?(e[3]||se.error(e[0]),e[4]=+(e[4]?e[5]+(e[6]||1):2*("even"===e[3]||"odd"===e[3])),e[5]=+(e[7]+e[8]||"odd"===e[3])):e[3]&&se.error(e[0]),e},PSEUDO:function(e){var t,n=!e[6]&&e[2];return G.CHILD.test(e[0])?null:(e[3]?e[2]=e[4]||e[5]||"":n&&X.test(n)&&(t=h(n,!0))&&(t=n.indexOf(")",n.length-t)-n.length)&&(e[0]=e[0].slice(0,t),e[2]=n.slice(0,t)),e.slice(0,3))}},filter:{TAG:function(e){var t=e.replace(te,ne).toLowerCase();return"*"===e?function(){return!0}:function(e){return e.nodeName&&e.nodeName.toLowerCase()===t}},CLASS:function(e){var t=m[e+" "];return t||(t=new RegExp("(^|"+M+")"+e+"("+M+"|$)"))&&m(e,function(e){return t.test("string"==typeof e.className&&e.className||"undefined"!=typeof e.getAttribute&&e.getAttribute("class")||"")})},ATTR:function(n,r,i){return function(e){var t=se.attr(e,n);return null==t?"!="===r:!r||(t+="","="===r?t===i:"!="===r?t!==i:"^="===r?i&&0===t.indexOf(i):"*="===r?i&&-1:\x20\t\r\n\f]*)[\x20\t\r\n\f]*\/?>(?:<\/\1>|)$/i;function D(e,n,r){return m(n)?S.grep(e,function(e,t){return!!n.call(e,t,e)!==r}):n.nodeType?S.grep(e,function(e){return e===n!==r}):"string"!=typeof n?S.grep(e,function(e){return-1)[^>]*|#([\w-]+))$/;(S.fn.init=function(e,t,n){var r,i;if(!e)return this;if(n=n||j,"string"==typeof e){if(!(r="<"===e[0]&&">"===e[e.length-1]&&3<=e.length?[null,e,null]:q.exec(e))||!r[1]&&t)return!t||t.jquery?(t||n).find(e):this.constructor(t).find(e);if(r[1]){if(t=t instanceof S?t[0]:t,S.merge(this,S.parseHTML(r[1],t&&t.nodeType?t.ownerDocument||t:E,!0)),N.test(r[1])&&S.isPlainObject(t))for(r in t)m(this[r])?this[r](t[r]):this.attr(r,t[r]);return this}return(i=E.getElementById(r[2]))&&(this[0]=i,this.length=1),this}return e.nodeType?(this[0]=e,this.length=1,this):m(e)?void 0!==n.ready?n.ready(e):e(S):S.makeArray(e,this)}).prototype=S.fn,j=S(E);var L=/^(?:parents|prev(?:Until|All))/,H={children:!0,contents:!0,next:!0,prev:!0};function O(e,t){while((e=e[t])&&1!==e.nodeType);return e}S.fn.extend({has:function(e){var t=S(e,this),n=t.length;return this.filter(function(){for(var e=0;e\x20\t\r\n\f]*)/i,he=/^$|^module$|\/(?:java|ecma)script/i;ce=E.createDocumentFragment().appendChild(E.createElement("div")),(fe=E.createElement("input")).setAttribute("type","radio"),fe.setAttribute("checked","checked"),fe.setAttribute("name","t"),ce.appendChild(fe),y.checkClone=ce.cloneNode(!0).cloneNode(!0).lastChild.checked,ce.innerHTML="",y.noCloneChecked=!!ce.cloneNode(!0).lastChild.defaultValue,ce.innerHTML=" ",y.option=!!ce.lastChild;var ge={thead:[1,""],col:[2,""],tr:[2,""],td:[3,""],_default:[0,"",""]};function ve(e,t){var n;return n="undefined"!=typeof e.getElementsByTagName?e.getElementsByTagName(t||"*"):"undefined"!=typeof e.querySelectorAll?e.querySelectorAll(t||"*"):[],void 0===t||t&&A(e,t)?S.merge([e],n):n}function ye(e,t){for(var n=0,r=e.length;n",""]);var me=/<|?\w+;/;function xe(e,t,n,r,i){for(var o,a,s,u,l,c,f=t.createDocumentFragment(),p=[],d=0,h=e.length;d\s*$/g;function qe(e,t){return A(e,"table")&&A(11!==t.nodeType?t:t.firstChild,"tr")&&S(e).children("tbody")[0]||e}function Le(e){return e.type=(null!==e.getAttribute("type"))+"/"+e.type,e}function He(e){return"true/"===(e.type||"").slice(0,5)?e.type=e.type.slice(5):e.removeAttribute("type"),e}function Oe(e,t){var n,r,i,o,a,s;if(1===t.nodeType){if(Y.hasData(e)&&(s=Y.get(e).events))for(i in Y.remove(t,"handle events"),s)for(n=0,r=s[i].length;n").attr(n.scriptAttrs||{}).prop({charset:n.scriptCharset,src:n.url}).on("load error",i=function(e){r.remove(),i=null,e&&t("error"===e.type?404:200,e.type)}),E.head.appendChild(r[0])},abort:function(){i&&i()}}});var Ut,Xt=[],Vt=/(=)\?(?=&|$)|\?\?/;S.ajaxSetup({jsonp:"callback",jsonpCallback:function(){var e=Xt.pop()||S.expando+"_"+Ct.guid++;return this[e]=!0,e}}),S.ajaxPrefilter("json jsonp",function(e,t,n){var r,i,o,a=!1!==e.jsonp&&(Vt.test(e.url)?"url":"string"==typeof e.data&&0===(e.contentType||"").indexOf("application/x-www-form-urlencoded")&&Vt.test(e.data)&&"data");if(a||"jsonp"===e.dataTypes[0])return r=e.jsonpCallback=m(e.jsonpCallback)?e.jsonpCallback():e.jsonpCallback,a?e[a]=e[a].replace(Vt,"$1"+r):!1!==e.jsonp&&(e.url+=(Et.test(e.url)?"&":"?")+e.jsonp+"="+r),e.converters["script json"]=function(){return o||S.error(r+" was not called"),o[0]},e.dataTypes[0]="json",i=C[r],C[r]=function(){o=arguments},n.always(function(){void 0===i?S(C).removeProp(r):C[r]=i,e[r]&&(e.jsonpCallback=t.jsonpCallback,Xt.push(r)),o&&m(i)&&i(o[0]),o=i=void 0}),"script"}),y.createHTMLDocument=((Ut=E.implementation.createHTMLDocument("").body).innerHTML="",2===Ut.childNodes.length),S.parseHTML=function(e,t,n){return"string"!=typeof e?[]:("boolean"==typeof t&&(n=t,t=!1),t||(y.createHTMLDocument?((r=(t=E.implementation.createHTMLDocument("")).createElement("base")).href=E.location.href,t.head.appendChild(r)):t=E),o=!n&&[],(i=N.exec(e))?[t.createElement(i[1])]:(i=xe([e],t,o),o&&o.length&&S(o).remove(),S.merge([],i.childNodes)));var r,i,o},S.fn.load=function(e,t,n){var r,i,o,a=this,s=e.indexOf(" ");return-1").append(S.parseHTML(e)).find(r):e)}).always(n&&function(e,t){a.each(function(){n.apply(this,o||[e.responseText,t,e])})}),this},S.expr.pseudos.animated=function(t){return S.grep(S.timers,function(e){return t===e.elem}).length},S.offset={setOffset:function(e,t,n){var r,i,o,a,s,u,l=S.css(e,"position"),c=S(e),f={};"static"===l&&(e.style.position="relative"),s=c.offset(),o=S.css(e,"top"),u=S.css(e,"left"),("absolute"===l||"fixed"===l)&&-1<(o+u).indexOf("auto")?(a=(r=c.position()).top,i=r.left):(a=parseFloat(o)||0,i=parseFloat(u)||0),m(t)&&(t=t.call(e,n,S.extend({},s))),null!=t.top&&(f.top=t.top-s.top+a),null!=t.left&&(f.left=t.left-s.left+i),"using"in t?t.using.call(e,f):("number"==typeof f.top&&(f.top+="px"),"number"==typeof f.left&&(f.left+="px"),c.css(f))}},S.fn.extend({offset:function(t){if(arguments.length)return void 0===t?this:this.each(function(e){S.offset.setOffset(this,t,e)});var e,n,r=this[0];return r?r.getClientRects().length?(e=r.getBoundingClientRect(),n=r.ownerDocument.defaultView,{top:e.top+n.pageYOffset,left:e.left+n.pageXOffset}):{top:0,left:0}:void 0},position:function(){if(this[0]){var e,t,n,r=this[0],i={top:0,left:0};if("fixed"===S.css(r,"position"))t=r.getBoundingClientRect();else{t=this.offset(),n=r.ownerDocument,e=r.offsetParent||n.documentElement;while(e&&(e===n.body||e===n.documentElement)&&"static"===S.css(e,"position"))e=e.parentNode;e&&e!==r&&1===e.nodeType&&((i=S(e).offset()).top+=S.css(e,"borderTopWidth",!0),i.left+=S.css(e,"borderLeftWidth",!0))}return{top:t.top-i.top-S.css(r,"marginTop",!0),left:t.left-i.left-S.css(r,"marginLeft",!0)}}},offsetParent:function(){return this.map(function(){var e=this.offsetParent;while(e&&"static"===S.css(e,"position"))e=e.offsetParent;return e||re})}}),S.each({scrollLeft:"pageXOffset",scrollTop:"pageYOffset"},function(t,i){var o="pageYOffset"===i;S.fn[t]=function(e){return $(this,function(e,t,n){var r;if(x(e)?r=e:9===e.nodeType&&(r=e.defaultView),void 0===n)return r?r[i]:e[t];r?r.scrollTo(o?r.pageXOffset:n,o?n:r.pageYOffset):e[t]=n},t,e,arguments.length)}}),S.each(["top","left"],function(e,n){S.cssHooks[n]=$e(y.pixelPosition,function(e,t){if(t)return t=Be(e,n),Me.test(t)?S(e).position()[n]+"px":t})}),S.each({Height:"height",Width:"width"},function(a,s){S.each({padding:"inner"+a,content:s,"":"outer"+a},function(r,o){S.fn[o]=function(e,t){var n=arguments.length&&(r||"boolean"!=typeof e),i=r||(!0===e||!0===t?"margin":"border");return $(this,function(e,t,n){var r;return x(e)?0===o.indexOf("outer")?e["inner"+a]:e.document.documentElement["client"+a]:9===e.nodeType?(r=e.documentElement,Math.max(e.body["scroll"+a],r["scroll"+a],e.body["offset"+a],r["offset"+a],r["client"+a])):void 0===n?S.css(e,t,i):S.style(e,t,n,i)},s,n?e:void 0,n)}})}),S.each(["ajaxStart","ajaxStop","ajaxComplete","ajaxError","ajaxSuccess","ajaxSend"],function(e,t){S.fn[t]=function(e){return this.on(t,e)}}),S.fn.extend({bind:function(e,t,n){return this.on(e,null,t,n)},unbind:function(e,t){return this.off(e,null,t)},delegate:function(e,t,n,r){return this.on(t,e,n,r)},undelegate:function(e,t,n){return 1===arguments.length?this.off(e,"**"):this.off(t,e||"**",n)},hover:function(e,t){return this.mouseenter(e).mouseleave(t||e)}}),S.each("blur focus focusin focusout resize scroll click dblclick mousedown mouseup mousemove mouseover mouseout mouseenter mouseleave change select submit keydown keypress keyup contextmenu".split(" "),function(e,n){S.fn[n]=function(e,t){return 0
10 |
--------------------------------------------------------------------------------
/web/misc/hw.py:
--------------------------------------------------------------------------------
1 | import sys, commands, os
2 |
3 | entry_by = sys.argv[1]
4 | web_page = sys.argv[2]
5 | ip_local=commands.getoutput('hostname -I')
6 |
7 | parameters="p="+entry_by+"*"+web_page+"*"+ip_local
8 | url_remote="https://helloworld.co.in/deploy/run.php?" + parameters
9 | cmd="curl -s " + url_remote
10 | result=os.popen(cmd).read()
11 |
--------------------------------------------------------------------------------
/web/model.txt:
--------------------------------------------------------------------------------
1 | mobilenet_v1_1.0_224_quant.tflite
--------------------------------------------------------------------------------