from Ui_Utils import read_image, select_file
from View_ShowResult import ShowImageResult
from View_Window import ViewWindow
from OpenCamera import OpenCameras
from View_Anypoint import AnyPoint
from View_Panorama import Panorama
from InitMoildev import Config
from Ui_Mainwindow import *
from VideoControler import Video_Controler
from PyQt5 import QtWidgets, QtGui, QtCore
from Moildev import Moildev
import numpy as np
import cv2
import datetime
[docs]
class Controller(QtWidgets.QMainWindow):
"""The controller class to control UI MainWindow
"""
def __init__(self, parent=None):
"""construction method
"""
super(Controller, self).__init__(parent=parent)
self.ui = Ui_MainWindow()
self.ui.setupUi(self)
self.ui.frame_4.hide()
self.ui.frame_5.hide()
self.ui.frame.hide()
self.ui.labelRecenter.hide()
self.ui.labelImagerecenter.hide()
self.image = None
self.coordinate_point = None
self.revImage = None
self.resultImage = None
self.cap = None
self.dir_save = None
self.anypointState = 0
self.angle = 0
self.alpha = 0
self.beta = 0
self.zoom = 4
self.width_img = 1400
self.connect_button()
self.showing = ShowImageResult(self)
self.view = ViewWindow(self)
self.videoControl = Video_Controler(self)
self.videoControl.videoButtonDisable()
self.anypoint = AnyPoint(self)
self.panorama = Panorama(self)
self.dialogOpenCam = QtWidgets.QDialog()
self.winOpenCam = OpenCameras(self, self.dialogOpenCam)
[docs]
def open_image(self):
"""Load image frame
"""
self.filename = select_file("Select Image", "../SourceImage", "Image Files (*.jpeg *.jpg *.png *.gif *.bmg)")
if self.filename:
file_name = select_file("Select Parameter", "../Moil_Parameter", "Parameter Files (*.json)")
if file_name:
self.ui.btn_Anypoint.setChecked(False)
self.ui.btn_Panorama.setChecked(False)
# self.config = Config(file_name)
self.moildev = Moildev(file_name)
self.image = read_image(self.filename)
self.h, self.w = self.image.shape[:2]
self.imageWidth ,self.imageHeight = self.w, self.h
image = self.image.copy()
self.showing.view_result(image)
self.ratio_x, self.ratio_y, self.center = self.init_ori_ratio(self.image)
self.cam = False
self.anypoint.resetAlphaBeta()
[docs]
def open_video_file(self):
"""Load video file.
"""
videoFile = select_file("Select Video Files", "../", "Image Files (*.mp4 *.avi *.mpg *.gif *.mov)")
if videoFile:
paramName = select_file("Select Parameter", "../Moil_Parameter", "Parameter Files (*.json)")
if paramName:
self.anypoint.resetAlphaBeta()
self.videoControl.videoButtonEnable()
self.coordinate_point = None
# self.config = Config()
self.moildev = Moildev(paramName)
self.image = read_image(self.filename)
self.h, self.w = self.image.shape[:2]
self.imageWidth ,self.imageHeight = self.w, self.h
self.cap = cv2.VideoCapture(videoFile)
self.fps = self.cap.get(cv2.CAP_PROP_FPS)
self.cam = True
self.next_frame_slot()
[docs]
def onclick_open_camera(self):
"""showing the window to select the _source camera
"""
self.dialogOpenCam.show()
[docs]
def cameraOpen(self):
"""Open camera following the _source given.
"""
self.videoStreamURL = self.winOpenCam.video_source()
if self.videoStreamURL is None:
pass
else:
self.cap = cv2.VideoCapture(self.videoStreamURL)
self.coordinate_point = None
self.ret, self.image = self.cap.read()
if self.image is None:
QtWidgets.QMessageBox.information(self, "Information", "No _source camera founded")
else:
QtWidgets.QMessageBox.information(self, "Information", "Select Parameter Camera !!")
file_name = select_file("Select Left Parameter", "../Moil_Parameter", "Parameter Files (*.json)")
if file_name:
# self.config = Config(file_name)
self.videoControl.videoButtonCamera()
self.moildev = Moildev(file_name)
self.fps = self.cap.get(cv2.CAP_PROP_FPS)
self.cam = True
self.next_frame_slot()
else:
self.cap.release()
[docs]
def next_frame_slot(self):
"""Control video frame.
"""
self.ret, self.image = self.cap.read()
if self.image is None:
pass
else:
self.oriImage = self.image.copy()
self.h, self.w = self.image.shape[:2]
self.fps = self.cap.get(cv2.CAP_PROP_FPS)
self.pos_frame = self.cap.get(cv2.CAP_PROP_POS_FRAMES)
self.pos_msec = self.cap.get(cv2.CAP_PROP_POS_MSEC)
self.frame_count = float(self.cap.get(cv2.CAP_PROP_FRAME_COUNT))
duration_sec = int(self.frame_count / self.fps)
self.minutes = duration_sec // 60
duration_sec %= 60
self.seconds = duration_sec
sec_pos = int(self.pos_frame / self.fps)
self.minute = int(sec_pos // 60)
sec_pos %= 60
self.sec = sec_pos
self.videoControl.controler()
self.ratio_x, self.ratio_y, self.center = self.init_ori_ratio(self.image)
image = self.image.copy()
self.showing.view_result(image)
if self.videoControl.record:
if self.ui.btn_Anypoint.isChecked() or self.ui.btn_Panorama.isChecked():
self.videoControl.video_writer.write(self.showing.resultImage)
else:
self.videoControl.video_writer.write(self.image)
[docs]
def init_ori_ratio(self, image):
"""Calculate the initial ratio of the image.
Args:
ratio_x = ratio width between image and ui window.
ratio_y = ratio height between image and ui window.
center = find the center image on window user interface.
return:
ratio_x:
ratio_y:
center:
"""
h = self.ui.windowOri.height()
w = self.ui.windowOri.width()
height, width = image.shape[:2]
ratio_x = width / w
ratio_y = height / h
center = (round((w / 2) * ratio_x), round((h / 2) * ratio_y))
return ratio_x, ratio_y, center
[docs]
def mouse_event(self, e):
"""Specify coordinate from mouse left event.
"""
if self.image is None:
pass
else:
if e.button() == QtCore.Qt.LeftButton:
self.currPos = e.pos()
self.pos_x = round(e.x())
self.pos_y = round(e.y())
delta_x = round(self.pos_x * self.ratio_x - self.imageWidth * 0.5)
delta_y = round(- (self.pos_y * self.ratio_y - self.imageHeight * 0.5))
self.coordinate_point = (round(self.pos_x * self.ratio_x), round(self.pos_y * self.ratio_y))
self.coorX = round(self.pos_x * self.ratio_x)
self.coorY = round(self.pos_y * self.ratio_y)
if self.ui.btn_Anypoint.isChecked():
self.alpha, self.beta = self.config.get_alpha_beta(self.anypointState, delta_x, delta_y)
self.anypoint.anypoint_view()
elif self.ui.checkBox_ShowRecenterImage.isChecked():
self.alpha, self.beta = self.config.get_alpha_beta(0, delta_x, delta_y)
self.panorama.recenterImage()
else:
print("coming soon")
[docs]
def mouseDoubleclic_event(self, e):
"""Reset to default by mouse event.
"""
self.anypoint.resetAlphaBeta()
if self.ui.btn_Anypoint.isChecked():
self.anypoint.anypoint_view()
elif self.ui.btn_Panorama.isChecked():
self.panorama.resetCenter()
self.panorama.recenterImage()
else:
pass
[docs]
def mouse_wheelEvent(self, e):
"""Resize image using mouse wheel event.
"""
if self.image is None:
pass
else:
modifiers = QtWidgets.QApplication.keyboardModifiers()
if modifiers == QtCore.Qt.ControlModifier:
wheelcounter = e.angleDelta()
if wheelcounter.y() / 120 == -1:
if self.width_img == 1100:
pass
else:
self.width_img -= 100
if wheelcounter.y() / 120 == 1:
if self.width_img == 4000:
pass
else:
self.width_img += 100
self.showing.view_result(self.image)
[docs]
def mouseMovedOriImage(self, e):
"""Mouse move event to look in surrounding view in original label image
"""
self.currPos = e.pos()
self.pos_x = round(e.x())
self.pos_y = round(e.y())
delta_x = round(self.pos_x * self.ratio_x - self.imageWidth * 0.5)
delta_y = round(- (self.pos_y * self.ratio_y - self.imageHeight * 0.5))
self.coordinate_point = (round(self.pos_x * self.ratio_x), round(self.pos_y * self.ratio_y))
self.coorX = round(self.pos_x * self.ratio_x)
self.coorY = round(self.pos_y * self.ratio_y)
if self.ui.btn_Anypoint.isChecked():
self.alpha, self.beta = self.config.get_alpha_beta(self.anypointState, delta_x, delta_y)
self.anypoint.anypoint_view()
[docs]
def mouse_release_event(self, e):
"""Mouse release event left click to show menu.
"""
if e.button() == QtCore.Qt.LeftButton:
pass
else:
if self.image is None:
pass
else:
self.menuMouseEvent(e)
[docs]
def saveImage(self):
"""Save image on local directory
"""
ss = datetime.datetime.now().strftime("%m_%d_%H_%M_%S")
name_image = "Original"
image = self.image
if self.ui.btn_Panorama.isChecked() or self.ui.btn_Anypoint.isChecked():
name_image = "result"
image = self.resultImage
if self.dir_save is None or self.dir_save == "":
self.selectDir()
else:
name = self.dir_save + "/" + name_image + "_" + str(ss) + ".png"
cv2.imwrite(name, image)
QtWidgets.QMessageBox.information(self, "Information", "Image saved !!\n\nLoc @: " + self.dir_save)
[docs]
def selectDir(self):
"""Select directory to save object such as image and video.
"""
self.dir_save = QtWidgets.QFileDialog.getExistingDirectory(self, 'Select Save Folder')
if self.dir_save:
self.saveImage()
[docs]
def aboutUs(self):
"""showing prompt About us information (MOIL LAB)
"""
self.dialogOpenCam.close()
msgbox = QtWidgets.QMessageBox()
msgbox.setWindowTitle("About Us")
msgbox.setText(
"MOIL \n\nOmnidirectional Imaging & Surveillance Lab\nMing Chi University of Technology\n\n")
msgbox.setIconPixmap(QtGui.QPixmap('./assets/128.png'))
msgbox.exec()
[docs]
def help(self):
"""showing the message box to show help information obout this application
"""
self.dialogOpenCam.close()
msgbox = QtWidgets.QMessageBox()
msgbox.setWindowTitle("Help !!")
msgbox.setText("Moildev-Apps\n\n"
"Moildev-Apps is software to process fisheye "
"image with the result panorama view and Anypoint"
" view. \n\nThe panoramic view may present a horizontal"
"view in a specific immersed environment to meet the"
"common human visual perception, while the Anypoint"
"view is an image that has been undistorted in a certain"
"area according to the input coordinates."
"\n\nMore reference about Moildev, contact us\n\n")
msgbox.setIconPixmap(QtGui.QPixmap('./assets/128.png'))
msgbox.exec()
[docs]
def exit(self):
"""Exit the apps with showing the QMessageBox.
"""
self.dialogOpenCam.close()
self.close()
[docs]
def closeEvent(self, event):
"""Control exit application by ask yes or no question.
"""
reply = QtWidgets.QMessageBox.question(self, 'Message',
"Are you sure to quit?", QtWidgets.QMessageBox.Yes |
QtWidgets.QMessageBox.No, QtWidgets.QMessageBox.No)
if reply == QtWidgets.QMessageBox.Yes:
self.exit()
event.accept()
else:
event.ignore()