2020-10-23 22:14:43 +00:00
|
|
|
from Application.Layer import Layer
|
|
|
|
|
from Application.Config import Config
|
|
|
|
|
from Application.VideoReader import VideoReader
|
|
|
|
|
from Application.Exporter import Exporter
|
|
|
|
|
from multiprocessing.pool import ThreadPool
|
2020-10-31 19:36:43 +00:00
|
|
|
from Application.Classifiers.Classifier import Classifier
|
2020-10-23 22:14:43 +00:00
|
|
|
import cv2
|
|
|
|
|
import numpy as np
|
2020-10-31 19:36:43 +00:00
|
|
|
import time
|
2020-12-05 19:57:24 +00:00
|
|
|
|
2020-10-23 22:14:43 +00:00
|
|
|
class LayerManager:
|
|
|
|
|
def __init__(self, config, layers):
|
|
|
|
|
self.data = {}
|
|
|
|
|
self.layers = layers
|
|
|
|
|
self.tolerance = config["tolerance"]
|
|
|
|
|
self.ttolerance = config["ttolerance"]
|
|
|
|
|
self.minLayerLength = config["minLayerLength"]
|
|
|
|
|
self.maxLayerLength = config["maxLayerLength"]
|
|
|
|
|
self.resizeWidth = config["resizeWidth"]
|
|
|
|
|
self.footagePath = config["inputPath"]
|
|
|
|
|
self.config = config
|
2020-12-18 20:27:19 +00:00
|
|
|
#self.classifier = Classifier()
|
2020-10-31 19:36:43 +00:00
|
|
|
self.tags = []
|
2020-10-23 22:14:43 +00:00
|
|
|
print("LayerManager constructed")
|
|
|
|
|
|
2020-11-11 21:32:12 +00:00
|
|
|
def transformLayers(self):
|
2020-11-05 22:17:05 +00:00
|
|
|
print("'Cleaning' Layers")
|
2020-12-18 20:27:19 +00:00
|
|
|
print("Before deleting short layers ", len(self.layers))
|
2020-10-23 22:14:43 +00:00
|
|
|
self.freeMin()
|
2020-12-18 20:27:19 +00:00
|
|
|
print("Before deleting long layers ", len(self.layers))
|
2020-10-23 22:14:43 +00:00
|
|
|
self.freeMax()
|
2020-12-18 20:27:19 +00:00
|
|
|
self.sortLayers()
|
2020-11-11 21:32:12 +00:00
|
|
|
self.calcStats()
|
2021-02-05 19:04:10 +00:00
|
|
|
print("Before deleting sparse layers ", len(self.layers))
|
2020-12-18 20:27:19 +00:00
|
|
|
self.deleteSparse()
|
|
|
|
|
print("after deleting sparse layers ", len(self.layers))
|
2021-02-06 14:49:46 +00:00
|
|
|
self.calcTimeOffset()
|
2020-12-18 20:27:19 +00:00
|
|
|
|
|
|
|
|
def deleteSparse(self):
|
|
|
|
|
toDelete = []
|
|
|
|
|
for i, l in enumerate(self.layers):
|
|
|
|
|
empty = l.bounds.count([])
|
2021-02-05 19:04:10 +00:00
|
|
|
if empty / len(l) > 0.5:
|
2020-12-18 20:27:19 +00:00
|
|
|
toDelete.append(i)
|
|
|
|
|
|
|
|
|
|
for i, id in enumerate(toDelete):
|
|
|
|
|
del self.layers[id - i]
|
2020-11-11 21:32:12 +00:00
|
|
|
|
|
|
|
|
def calcStats(self):
|
|
|
|
|
for layer in self.layers:
|
|
|
|
|
layer.calcStats()
|
2020-10-23 22:14:43 +00:00
|
|
|
|
|
|
|
|
def freeMin(self):
|
|
|
|
|
self.data.clear()
|
|
|
|
|
layers = []
|
|
|
|
|
for l in self.layers:
|
2020-12-18 20:27:19 +00:00
|
|
|
if len(l) > self.minLayerLength:
|
2020-10-23 22:14:43 +00:00
|
|
|
layers.append(l)
|
|
|
|
|
self.layers = layers
|
2020-10-31 19:36:43 +00:00
|
|
|
|
2020-10-23 22:14:43 +00:00
|
|
|
def freeMax(self):
|
|
|
|
|
layers = []
|
|
|
|
|
for l in self.layers:
|
2020-12-18 20:27:19 +00:00
|
|
|
if len(l) < self.maxLayerLength:
|
2020-10-23 22:14:43 +00:00
|
|
|
layers.append(l)
|
|
|
|
|
self.layers = layers
|
|
|
|
|
|
2020-10-31 19:36:43 +00:00
|
|
|
def tagLayers(self):
|
|
|
|
|
'''Use classifieres the tag all Layers, by reading the contour content from the original video, then applying the classifier'''
|
2020-11-05 22:17:05 +00:00
|
|
|
print("Tagging Layers")
|
2020-10-31 19:36:43 +00:00
|
|
|
exporter = Exporter(self.config)
|
|
|
|
|
start = time.time()
|
2020-12-26 13:58:58 +00:00
|
|
|
for i, layer in enumerate(self.layers):
|
2020-10-31 19:36:43 +00:00
|
|
|
print(f"{round(i/len(self.layers)*100,2)} {round((time.time() - start), 2)}")
|
|
|
|
|
start = time.time()
|
|
|
|
|
if len(layer.bounds[0]) == 0:
|
|
|
|
|
continue
|
|
|
|
|
listOfFrames = exporter.makeListOfFrames([layer])
|
2020-10-23 22:14:43 +00:00
|
|
|
|
2020-10-31 19:36:43 +00:00
|
|
|
videoReader = VideoReader(self.config, listOfFrames)
|
|
|
|
|
videoReader.fillBuffer()
|
2020-10-23 22:14:43 +00:00
|
|
|
|
2020-10-31 19:36:43 +00:00
|
|
|
while not videoReader.videoEnded():
|
|
|
|
|
frameCount, frame = videoReader.pop()
|
|
|
|
|
frame = cv2.cvtColor(frame, cv2.COLOR_BGR2RGB)
|
|
|
|
|
data = []
|
|
|
|
|
for (x, y, w, h) in layer.bounds[frameCount - layer.startFrame]:
|
|
|
|
|
if x is None:
|
|
|
|
|
break
|
|
|
|
|
factor = videoReader.w / self.resizeWidth
|
|
|
|
|
x = int(x * factor)
|
|
|
|
|
y = int(y * factor)
|
|
|
|
|
w = int(w * factor)
|
|
|
|
|
h = int(h * factor)
|
|
|
|
|
data.append(np.copy(frame[y:y+h, x:x+w]))
|
|
|
|
|
layer.data.append(data)
|
|
|
|
|
tags = self.classifier.tagLayer(layer.data)
|
|
|
|
|
print(tags)
|
|
|
|
|
self.tags.append(tags)
|
2020-10-23 22:14:43 +00:00
|
|
|
|
2020-10-31 19:36:43 +00:00
|
|
|
videoReader.thread.join()
|
2020-10-23 22:14:43 +00:00
|
|
|
|
|
|
|
|
def sortLayers(self):
|
|
|
|
|
self.layers.sort(key = lambda c:c.startFrame)
|
2021-02-06 14:49:46 +00:00
|
|
|
|
|
|
|
|
def calcTimeOffset(self):
|
|
|
|
|
for i, layer in enumerate(self.layers):
|
|
|
|
|
overlap = True
|
|
|
|
|
while overlap:
|
|
|
|
|
overlap = False
|
|
|
|
|
for l in self.layers[i:]:
|
|
|
|
|
if layer.timeOverlaps(l):
|
|
|
|
|
if layer.spaceOverlaps(l):
|
|
|
|
|
overlap = True
|
|
|
|
|
if overlap:
|
|
|
|
|
self.addDelay(i, 10)
|
|
|
|
|
|
|
|
|
|
if self.layers[i].exportOffset >= 180:
|
|
|
|
|
break
|
|
|
|
|
|
|
|
|
|
def addDelay(self, index, frames):
|
|
|
|
|
for layer in self.layers[index:]:
|
|
|
|
|
layer.exportOffset += frames
|