Ejemplo n.º 1
0
class SerialThread(QThread):
    # define a signal, when cam opens, emit this signal

    def __init__(self):
        super(SerialThread, self).__init__()
        #        self.tnum = num
        self.isstop = True
        self.cond = QWaitCondition()
        self.mutex = QMutex()
        # self.sensor = ControlBoard()

    def __del__(self):
        # 线程状态改变与线程终止
        self.isstop = True
        self.quit()

    def pause(self):
        #        print("thread pause")
        self.isstop = True

    def resume(self):
        self.isstop = False
        self.cond.wakeAll()

    def run(self):
        pass
Ejemplo n.º 2
0
class LoadingBarThread(QThread):
    change_value = pyqtSignal(int)

    def __init__(self, parent, limit):
        QThread.__init__(self)
        self.cond = QWaitCondition()
        self.mutex = QMutex()
        self.is_running = True
        self.limit = limit
        self.parent = parent

    def __del__(self):
        self.wait()

    def run(self):
        self.cnt = 0
        while True:
            self.mutex.lock()

            if not self.is_running:
                self.cond.wait(self.mutex)

            if self.cnt == self.limit:
                self.toggle_status()

            self.cnt += 1
            self.change_value.emit(self.cnt)
            self.msleep(10)

            self.mutex.unlock()

    def toggle_status(self):
        self.is_running = not self.is_running
        if self.is_running:
            self.cond.wakeAll()
Ejemplo n.º 3
0
class ConsoleInitThread(QObject):
    initialized = pyqtSignal(object, object)

    def __init__(self, *args, **kwargs):
        super(ConsoleInitThread, self).__init__(*args, **kwargs)
        self.mutex = QMutex()
        self.wait_condition = QWaitCondition()

    def run(self):
        self.mutex.lock()
        kernel_manager = QtKernelManager(kernel_name="""python3""")
        kernel_manager.start_kernel()

        kernel_client = kernel_manager.client()
        kernel_client.start_channels()

        # notify to update ui
        self.initialized.emit(kernel_manager, kernel_client)

        # wait for exit
        self.wait_condition.wait(self.mutex)
        self.mutex.unlock()

        # stop channels and kernel
        kernel_client.stop_channels()
        kernel_manager.shutdown_kernel()

    def stop(self):
        self.wait_condition.wakeAll()
Ejemplo n.º 4
0
class SharedData:
    """
    Provides access to shared data
    between Window and Classifier
    """

    def __init__(self):
        self._mutex = QMutex()
        self._data = None
        self._data_available = QWaitCondition()

    def consume(self):
        self._mutex.lock()
        if self._data is None:
            self._data_available.wait(self._mutex)
        result = self._data
        self._data = None
        self._mutex.unlock()
        return result

    def provide(self, data):
        self._mutex.lock()
        self._data = data
        self._data_available.wakeAll()
        self._mutex.unlock()
Ejemplo n.º 5
0
class WorkerThread(QThread):
    def __init__(self):
        QThread.__init__(self)
        self.cond = QWaitCondition()
        self.mutex = QMutex()
        self._status = False
        self.userID = ""

    def __del__(self):
        self.wait()

    def run(self):
        while True:
            self.mutex.lock()
            print("start thread")

            if not self._status:
                self.cond.wait(self.mutex)
            #print(userID)
            recordingSnd.recording(self.userID)
            print("going to another work")

            self.msleep(100)

            self.mutex.unlock()

    def toggle_status(self, userID):
        self.userID = userID
        self._status = not self._status
        if self._status:
            self.cond.wakeAll()

    @property
    def status(self):
        return self._status
Ejemplo n.º 6
0
class Thread(QThread):

    valueChange = pyqtSignal(int)

    def __init__(self, *args, **kwargs):
        super(Thread, self).__init__(*args, **kwargs)
        self._isPause = False
        self._value = 0
        self.cond = QWaitCondition()
        self.mutex = QMutex()

    def pause(self):
        self._isPause = True

    def resume(self):
        self._isPause = False
        self.cond.wakeAll()

    def run(self):
        while 1:
            self.mutex.lock()
            if self._isPause:
                self.cond.wait(self.mutex)
            if self._value > 100:
                self._value = 0
            self._value += 1
            self.valueChange.emit(self._value)
            self.msleep(100)
            self.mutex.unlock()
Ejemplo n.º 7
0
class Thread(QThread):
    signal_update = pyqtSignal()

    def __init__(self, window):
        QThread.__init__(self)
        self.cond = QWaitCondition()
        self.mutex = QMutex()
        self.cnt = 0
        self._status = True
        self.window = window
        self.logger = Logger(window)

    def __del__(self):
        self.wait()

    def run(self):
        while True:
            self.mutex.lock()
            if not self._status:
                self.cond.wait(self.mutex)
            # self.logger.print_log("working auto bot")
            self.msleep(1000)  # ※주의 QThread에서 제공하는 sleep을 사용
            self.signal_update.emit()
            self.mutex.unlock()

    def toggle_status(self):
        self._status = not self._status
        if self._status:
            self.cond.wakeAll()

    @property
    def status(self):
        return self._status
class DownloadManager(QThread):
    imagesLoaded = QtCore.pyqtSignal(list)
    downloadFailed = QtCore.pyqtSignal(list)

    allDownloaded = QtCore.pyqtSignal()

    downloadPaused = QtCore.pyqtSignal()

    downloadResumed = QtCore.pyqtSignal()

    exceptionRaised = QtCore.pyqtSignal(str)

    def __init__(self, app_state):
        super().__init__()
        self.mutex = QMutex()
        self.download_paused = False
        self.wait_condition = QWaitCondition()

        self.stateful_downloader = StatefulDownloader(app_state)

        self._has_started = False

    def run(self):
        try:
            self._has_started = True

            stateful_downloader = self.stateful_downloader

            for result in stateful_downloader:
                self.imagesLoaded.emit(result.succeeded_urls)
                self.downloadFailed.emit(result.failed_urls)

                if self.download_paused:
                    self.downloadPaused.emit()
                    self.mutex.lock()
                    self.wait_condition.wait(self.mutex)
                    self.mutex.unlock()

            self.allDownloaded.emit()
        except WordNetIdsUnavailableError:
            msg = 'Failed to fetch a list of WordNet ids. ' \
                  'Check if ImageNet server can be reached'
            self.exceptionRaised.emit(msg)

    def pause_download(self):
        self.mutex.lock()
        self.download_paused = True
        self.mutex.unlock()

    def resume_download(self):
        if not self._has_started:
            self.start()
            return

        self.mutex.lock()
        self.download_paused = False
        self.mutex.unlock()
        self.wait_condition.wakeAll()
        self.downloadResumed.emit()
class ProjectedImageBuffer(object):
    """
    Class for synchronizing processing threads from different cameras.
    """
    def __init__(self, drop_if_full=True, buffer_size=8):
        self.drop_if_full = drop_if_full
        self.buffer = Buffer(buffer_size)
        self.sync_devices = set()
        self.wc = QWaitCondition()
        self.mutex = QMutex()
        self.arrived = 0
        self.current_frames = dict()

    def bind_thread(self, thread):
        with QMutexLocker(self.mutex):
            self.sync_devices.add(thread.device_id)

        name = thread.camera_model.camera_name
        shape = settings.project_shapes[name]
        self.current_frames[thread.device_id] = np.zeros(
            shape[::-1] + (3, ), np.uint8)
        thread.proc_buffer_manager = self

    def get(self):
        return self.buffer.get()

    def set_frame_for_device(self, device_id, frame):
        if device_id not in self.sync_devices:
            raise ValueError(
                "Device not held by the buffer: {}".format(device_id))
        self.current_frames[device_id] = frame

    def sync(self, device_id):
        # only perform sync if enabled for specified device/stream
        self.mutex.lock()
        if device_id in self.sync_devices:
            # increment arrived count
            self.arrived += 1
            # we are the last to arrive: wake all waiting threads
            if self.arrived == len(self.sync_devices):
                self.buffer.add(self.current_frames, self.drop_if_full)
                self.wc.wakeAll()
            # still waiting for other streams to arrive: wait
            else:
                self.wc.wait(self.mutex)
            # decrement arrived count
            self.arrived -= 1
        self.mutex.unlock()

    def wake_all(self):
        with QMutexLocker(self.mutex):
            self.wc.wakeAll()

    def __contains__(self, device_id):
        return device_id in self.sync_devices

    def __str__(self):
        return (self.__class__.__name__ + ":\n" + \
                "devices: {}\n".format(self.sync_devices))
Ejemplo n.º 10
0
class SerialReadThread(QThread):
    """
    시리얼 연결이 성공하면 항상 데이터를 수신할 수 있어야 하므로
    스레드로 만들어야 한다.

    """
    # 사용자 정의 시그널 선언
    # 받은 데이터 그대로를 전달 해주기 위해 QByteArray 형태로 전달
    received_data = pyqtSignal(QByteArray, name="receivedData")

    def __init__(self, serial):
        QThread.__init__(self)
        self.cond = QWaitCondition()
        self._status = False
        self.mutex = QMutex()
        self.serial = serial

    def __del__(self):
        self.wait()

    def run(self):
        """
        들어온 데이터가 있다면 시그널을 발생
        :return:
        """
        while True:
            self.mutex.lock()
            if not self._status:
                self.cond.wait(self.mutex)

            buf = self.serial.readAll()

            if buf:
                #print(buf)
                buf = bytes("Received : ",
                            "utf-8") + binascii.hexlify(buf) + bytes(
                                [0x0A])  # '0x0A(LF)'
                self.received_data.emit(buf)

            self.usleep(1)
            #buf = bytes([0x0A])
            #self.received_data.emit(buf)
            self.mutex.unlock()

    def toggle_status(self):
        self._status = not self._status
        if self._status:
            self.cond.wakeAll()

    @pyqtSlot(bool, name='setStatus')
    def set_status(self, status):
        self._status = status
        if self._status:
            self.cond.wakeAll()
Ejemplo n.º 11
0
class Classifier(QThread):
    signal_classify_done = pyqtSignal(str)

    def __init__(self):
        super().__init__()
        self._mutex = QMutex()
        self._abort = False
        self._condition = QWaitCondition()
        self.cur_img = None

        # load model and default graph
        self.classifier = keras.models.load_model('resnet_512.h5')
        self.graph = tf.get_default_graph()  # REALLY IMPORTANT

    def __del__(self):
        self._abort = True
        self.wait()

    def activate(self, img_np_arr):
        self.cur_img = img_np_arr
        print(type(self.cur_img))
        print(self.cur_img.shape)
        self._condition.wakeAll()

    def run(self):
        while True:
            if self._abort:
                return
            self._mutex.lock()
            self._condition.wait(self._mutex)
            # Doing thing
            if self.cur_img is None:
                continue
            # classify top3

            x = np.asarray([self.cur_img])
            res = ''
            with self.graph.as_default():
                predictions = self.classifier.predict(
                    x, batch_size=1)[0]  # note that predictions is a 2D array
                idx_max = np.argsort(predictions)
                top3 = idx_max[-1:-4:-1]
                for idx in top3:
                    res += '%s:%.2f,' % (classes_reader[idx], predictions[idx])

            # emit signal
            self.signal_classify_done.emit(res)
            # DONE DOING THING
            self._mutex.unlock()
Ejemplo n.º 12
0
class ThreadCapture(QThread):
    """
    단순히 0부터 100까지 카운트만 하는 쓰레드
    값이 변경되면 그 값을 change_value 시그널에 값을 emit 한다.
    """
    # 사용자 정의 시그널 선언
    captured_screen = pyqtSignal(QPixmap, name="capturedScreen")

    def __init__(self):
        QThread.__init__(self, parent=None)
        self.cond = QWaitCondition()
        self.mutex = QMutex()
        self.cnt = 0
        self._status = True

    def __del__(self):
        self.wait()

    def run(self):
        while True:
            self.mutex.lock()
            if not self._status:
                self.cond.wait(self.mutex)
            pixmap = self.capture()
            self.captured_screen(pixmap)
            self.msleep(100)  # ※주의 QThread에서 제공하는 sleep을 사용

            self.mutex.unlock()

    def capture(self):
        screen: QScreen = QGuiApplication.primaryScreen()
        window: QWindow = self.windowHandle()
        if window:
            screen = window.screen()
        if not screen:
            return
        pixmap = screen.grabWindow(0)
        return pixmap

    def toggle_status(self):
        self._status = not self._status
        if self._status:
            self.cond.wakeAll()

    @property
    def status(self):
        return self._status
Ejemplo n.º 13
0
class SerialWriteThread(QThread):

    # #########################################################################################
    #   initialize
    # #########################################################################################
    def __init__(self, serial, write_queue: queue.Queue):

        QThread.__init__(self)

        self.cond = QWaitCondition()
        self.mutex = QMutex()
        self._status = False
        self.serial = serial
        self.write_queue = write_queue

    def __del__(self):
        self.wait()

    # #########################################################################################
    #   쓰레드 시작
    # #########################################################################################
    def run(self):

        while True:

            self.mutex.lock()

            if not self._status:

                # 하위 실행 안됨
                self.cond.wait(self.mutex)

            if not self.write_queue.empty():
                self.serial.write(self.write_queue.get())

            self.usleep(1)
            self.mutex.unlock()

    # #########################################################################################
    #   쓰레드 활성/비화성
    # #########################################################################################
    @pyqtSlot(bool)
    def set_status(self, status):
        self._status = status
        if self._status:
            self.cond.wakeAll()
Ejemplo n.º 14
0
class SchedImportThread(QThread):
    message = pyqtSignal()

    def __init__(self, config):
        super(self.__class__, self).__init__()
        self.working = True
        self._config = config
        hh_mm = config.get('sched', 'time', fallback='18:00')
        x = hh_mm.split(':')
        self.hour = int(x[0])
        self.minute = int(x[1])
        self.cond = QWaitCondition()
        self.mutex = QMutex()

    def stop(self):
        if self.working:
            self.working = False
            self.cond.wakeAll()
            self.wait()

    def __del__(self):
        self.stop()

    def next_time_delta(self):
        now = Datetime.now()
        next_time = Datetime(now.year, now.month, now.day, self.hour,
                             self.minute)
        if next_time < now:
            current_date = Datetime(now.year, now.month, now.day)
            if current_date.day_of_week() == 5:
                next_time = next_time + TimeDelta(3)
            else:
                next_time = next_time + TimeDelta(1)
        return (next_time, next_time - now)

    @hku_catch()
    def run(self):
        self.mutex.tryLock()
        next_datetime, delta = self.next_time_delta()
        self.logger.info("下次导入时间:{}".format(next_datetime))
        delta = int(delta.total_milliseconds())
        while self.working and not self.cond.wait(self.mutex, int(delta)):
            self.message.emit()
            next_datetime, delta = self.next_time_delta()
            self.logger.info("下次导入时间:{}".format(next_datetime))
            delta = int(delta.total_milliseconds())
Ejemplo n.º 15
0
class RecordWindow(WindowBase, WindowUI):
    def __init__(self, parent=None):
        WindowBase.__init__(self, parent)
        self.mutex = QMutex()
        self.condition = QWaitCondition()
        self.mutex.lock()

        self.setupUi(self)

        self.recording = False
        logging.info("Initializing Manager......")
        self.manager = Manager(self.mutex, self.condition)

        logging.info("Connecting events.......")
        self.startStopButton.clicked.connect(self.onStartStopButtonPress)
        self.manager.connectEvents(timerEvent=self.timerEvent,
                                   videoFrameEvent=self.setFrame)
        self.manager.startVideo()

    def onStartStopButtonPress(self):
        if self.recording:
            self.manager.stopRecording()
            self.startStopButton.setText('start recording')
        else:
            self.manager.startRecording()
            self.startStopButton.setText("stop recording")
        self.recording = not self.recording

    def setFrame(self, frame):
        self.mutex.lock()
        try:
            w = self.videoScreen.width() - 1
            h = self.videoScreen.height() - 1
            pixmap = QtGui.QPixmap.fromImage(frame)
            self.videoScreen.setPixmap(
                pixmap.scaled(w, h, QtCore.Qt.KeepAspectRatio,
                              QtCore.Qt.FastTransformation))
            self.videoScreen.setMinimumSize(1, 1)
        finally:
            self.mutex.unlock()
            self.condition.wakeAll()

    def timerEvent(self):
        elapsedTime = self.manager.getElapsedTime()
        self.timerWindow.setText(elapsedTime.toString("mm:ss:zzz")[:8])
Ejemplo n.º 16
0
class SerialReadThread(QThread):
    """
    Should use QThread, because data always are transferred after connecting serial communication
    """

    #Custom Signal
    #transfer QByteArray type for communicating received data with same type

    def __init__(self, serial):
        QThread.__init__(self)
        self.cond = QWaitCondition()
        self._status = False
        self.mutex = QMutex()
        self.serial = serial

    def __del__(self):
        self.wait()

    def run(self):
        """
        if there is input data, generate signal
        :return:
        """

        while True:
            self.mutex.lock()
            if not self._status():
                self.cond.wait(self.mutex)

            buf = self.serial.readAll()
            if buf:
                self.received_data.emit(buf)
            self.usleep(1)
            self.mutex.unlock()

    def toggle_status(self):
        self._status = not self._status
        if self._status:
            self.cond.wakeAll()

    @pyqtSlot(bool, name='setStatus')
    def set_status(self, status):
        self._status = status
        if self._status:
            self.cond.wakeAll()
Ejemplo n.º 17
0
class LoadingBarThread(QThread):
    change_value = pyqtSignal(int)
    complete = pyqtSignal()

    def __init__(self, parent):
        QThread.__init__(self)
        self.cond = QWaitCondition()
        self.mutex = QMutex()
        self._status = True
        self.parent = parent

    def __del__(self):
        self.wait()

    def run(self):
        self.cnt = 0
        while True:
            self.mutex.lock()

            if not self._status:
                self.cond.wait(self.mutex)

            if 50 == self.cnt:
                self.toggle_status()

            if 100 == self.cnt:
                self.cnt = 0
                self.complete.emit()

            self.cnt += 1
            self.change_value.emit(self.cnt)
            self.msleep(10)

            self.mutex.unlock()

    def toggle_status(self):
        self._status = not self._status
        if self._status:
            self.cond.wakeAll()

    @property
    def status(self):
        return self._status
Ejemplo n.º 18
0
class EventThread(QThread):
    exeCnt = 0
    event = None

    def __init__(self, event):
        QThread.__init__(self)
        self.cond = None
        self.mutex = None
        self._status = True
        self.event = event

    def __del__(self):
        self.wait()

    def run(self):
        self.cond = QWaitCondition()
        self.mutex = QMutex()

        self.mutex.lock()

        # self.msleep(100)
        if not self._status:
            self.cond.wait(self.mutex)

        try:
            self.event()
        except Exception as e:
            print(e)
        finally:
            self.mutex.unlock()

    def toggle_status(self):
        self._status = not self._status
        if self._status:
            self.cond.wakeAll()

    @property
    def status(self):
        return self._status

    def stop(self):
        self.terminate()
Ejemplo n.º 19
0
class Thread(QThread):
    """
    # 단순히 0부터 100까지 카운트만 하는 쓰레드
    # 값이 변경되면 그 값을 change_value 시그널에 값을 emit 한다.
    """
    # 사용자 정의 시그널 선언
    change_value = pyqtSignal(int)

    def __init__(self):
        # QThread.__init__(self)
        super().__init__()
        self.cond = QWaitCondition()
        self.mutex = QMutex()
        self.cnt = 0
        self._status = True

    def __del__(self):
        self.wait()

    def run(self):
        while True:
            self.mutex.lock()

            if not self._status:
                self.cond.wait(self.mutex)

            if 100 == self.cnt:
                self.cnt = 0
            self.cnt += 1
            self.change_value.emit(self.cnt)
            self.msleep(100)  # ※주의 QThread에서 제공하는 sleep을 사용

            self.mutex.unlock()

    def toggle_status(self):
        self._status = not self._status
        if self._status:
            self.cond.wakeAll()

    @property
    def status(self):
        return self._status
Ejemplo n.º 20
0
class ReturnValue(Generic[T]):
    """Pass a return value from a slot back to the signal emitting thread.
    The ReturnValue has to be send with the signal, the receiving
    thread than calls .send() to set the value, while the calling
    thread calls .receive() to wait until the value arrives."""
    def __init__(self) -> None:
        self._mutex = QMutex()
        self._wait_condition = QWaitCondition()
        self._value: Optional[T] = None

    def receive(self) -> T:
        self._mutex.lock()
        while self._value is None:
            self._wait_condition.wait(self._mutex)
        self._mutex.unlock()

        return self._value

    def send(self, value: T) -> None:
        self._value = value
        self._wait_condition.wakeAll()
Ejemplo n.º 21
0
class Thread(QThread):

    valueChange = pyqtSignal(int)
    id_pipLine = pyqtSignal(list)
    task_finished = pyqtSignal()

    def __init__(self, results, *args, **kwargs):
        super(Thread, self).__init__(*args, **kwargs)
        # results 是从raw_datas查询的所有数据 一般以城市为条件查询
        self.results = results
        self._isPause = True
        self._value = 1
        self.cond = QWaitCondition()
        self.mutex = QMutex()

    def next(self):
        print("下一组数据")
        self._isPause = False
        self.cond.wakeAll()
        self._isPause = True

    def run(self):
        while True:
            self.mutex.lock()
            if self._isPause:

                for i in self.results:
                    id = i[0]
                    company_id = i[1]
                    job_id = i[2]
                    item = [id, company_id, job_id]
                    # print(item)
                    self.id_pipLine.emit(item)
                    self.cond.wait(self.mutex)
                    if self._value == len(self.results):
                        self.task_finished.emit()
                    print('第{}组'.format(self._value))
                    self.valueChange.emit(self._value)
                    self._value += 1
            self.mutex.unlock()
Ejemplo n.º 22
0
class WaitingData:
    def __init__(self):
        self.logger = logging.getLogger(constants.General.NAME)

        self.__mutex = QMutex()
        self.__condition = QWaitCondition()

        self.__data = None

    def wait(self):
        self.__mutex.lock()
        self.logger.debug(f'Lock: {self}')
        self.__condition.wait(self.__mutex)

    def wakeup(self, *args):
        self.__condition.wakeAll()
        self.__data = args

        self.logger.debug(f'Unlock: {self}. Data: {args}')

    def get_data(self) -> Optional[tuple]:
        return self.__data
Ejemplo n.º 23
0
class LogMultiThread(QThread):
    logViewFinished = pyqtSignal(list)
    logPagingFinished = pyqtSignal()

    def __init__(self, ip, tp, guid='', icnt_list=[]):
        QThread.__init__(self)
        self.cond = None
        self.mutex = None
        self._status = True
        self.ip = ip
        self.tp = tp
        self.guid = guid
        self.icnt_list = icnt_list

    def __del__(self):
        self.wait()

    def run(self):
        self.cond = QWaitCondition()
        #self.mutex = QMutex()
        #self.mutex.lock()

        #if not self._status:
        #    self.cond.wait(self.mutex)

        try:
            log_view = []

            for ix, icnt in enumerate(self.icnt_list):
                swgs_url = 'http://172.31.196.21:8060/websquare/Service/SVC?commonsvc=0&rtcode=0&Trx_code=ZORDSCOM06020_TR01&ScreenName=ZORDSCOM06020&fCloseAccount=0&LogLvlGbn=&G_BizCd=null&G_Biz_Start_Time=null&__smReqSeq=5&_useLayout=true'
                payload = {"input1": [{"fcnt": "0", "flag": "L", "guid": self.guid, "icnt": icnt, "ip_addr": self.ip, "rowStatus": "C", "tp_id": self.tp, "prod_skip": "N"}],
                             "HEAD":  {"Trx_Code": "ZORDSCOM06020_TR01",
                                       "Ngms_UserId": "1000852323",
                                       "Ngms_LogInId": "ENJOYHAN",
                                       "Ngms_EmpNum": "",
                                       "Ngms_OrgId": "A000700000",
                                       "Ngms_HrOrgCd": "",
                                       "Ngms_PostOrgCd": "A000700000",
                                       "Ngms_PostSaleOrgCd": "A000700000",
                                       "Ngms_SupSaleOrgCd": "A010890000",
                                       "Ngms_IpAddr": "150.28.65.76",
                                       "Ngms_BrTypCd": "450",
                                       "Ngms_AuthId": "",
                                       "Ngms_ConnOrgId": "A000700000",
                                       "Ngms_ConnOrgCd": "A000700000",
                                       "Ngms_ConnSaleOrgId": "A000700000",
                                       "Ngms_ConnSaleOrgCd": "A000700000",
                                       "Ngms_AuthTypPermCd": "EQ",
                                       "Ngms_PostSaleOrgId": "A000700000",
                                       "Ngms_SupSaleOrgId": "A010890000",
                                       "Term_Type": "0",
                                       "User_Term_Type": "",
                                       "St_Stop": "0",
                                       "St_Trace": "",
                                       "Stx_Dt": "",
                                       "Stx_Tm": "",
                                       "Etx_Dt": "",
                                       "Etx_Tm": "",
                                       "Rt_Cd": "",
                                       "Screen_Name": "ZORDSCOM06020",
                                       "Msg_Cnt": "0",
                                       "Handle_Id": "863017520 ",
                                       "Ngms_Filler1": "",
                                       "Ngms_CoClCd": "T",
                                       "Screen_Call_Trace": "Top-ZORDSCOM06020-ZORDSCOM06020_TR01",
                                       "rowStatus": "C"}}

                log_view_result = requests.get(swgs_url, json=payload)
                log_view_temp = log_view_result.json()
                log_view.extend(log_view_temp['output1'])

                self.logPagingFinished.emit()
                print('{}번 조회완료'.format(icnt))

        except Exception as e:
            print('log woker error')
            print(e)
        finally:
            self.logViewFinished.emit(log_view)
            pass

    def toggle_status(self):
        self._status = not self._status
        if self._status:
            self.cond.wakeAll()

    @property
    def status(self):
        return self._status

    def stop(self):
        self.terminate()
Ejemplo n.º 24
0
class VcsStatusMonitorThread(QThread):
    """
    Class implementing the VCS status monitor thread base class.
    
    @signal vcsStatusMonitorData(list of str) emitted to update the VCS status
    @signal vcsStatusMonitorStatus(str, str) emitted to signal the status of
        the monitoring thread (ok, nok, op) and a status message
    """
    vcsStatusMonitorData = pyqtSignal(list)
    vcsStatusMonitorStatus = pyqtSignal(str, str)
    
    def __init__(self, interval, project, vcs, parent=None):
        """
        Constructor
        
        @param interval new interval in seconds (integer)
        @param project reference to the project object (Project)
        @param vcs reference to the version control object
        @param parent reference to the parent object (QObject)
        """
        super(VcsStatusMonitorThread, self).__init__(parent)
        self.setObjectName("VcsStatusMonitorThread")
        
        self.setTerminationEnabled(True)
        
        self.projectDir = project.getProjectPath()
        self.project = project
        self.vcs = vcs
        
        self.interval = interval
        self.autoUpdate = False
        
        self.statusList = []
        self.reportedStates = {}
        self.shouldUpdate = False
        
        self.monitorMutex = QMutex()
        self.monitorCondition = QWaitCondition()
        self.__stopIt = False
    
    def run(self):
        """
        Public method implementing the tasks action.
        """
        while not self.__stopIt:
            # perform the checking task
            self.statusList = []
            self.vcsStatusMonitorStatus.emit(
                "wait", self.tr("Waiting for lock"))
            try:
                locked = self.vcs.vcsExecutionMutex.tryLock(5000)
            except TypeError:
                locked = self.vcs.vcsExecutionMutex.tryLock()
            if locked:
                try:
                    self.vcsStatusMonitorStatus.emit(
                        "op", self.tr("Checking repository status"))
                    res, statusMsg = self._performMonitor()
                finally:
                    self.vcs.vcsExecutionMutex.unlock()
                if res:
                    status = "ok"
                else:
                    status = "nok"
                self.vcsStatusMonitorStatus.emit(
                    "send", self.tr("Sending data"))
                self.vcsStatusMonitorData.emit(self.statusList)
                self.vcsStatusMonitorStatus.emit(status, statusMsg)
            else:
                self.vcsStatusMonitorStatus.emit(
                    "timeout", self.tr("Timed out waiting for lock"))
            
            if self.autoUpdate and self.shouldUpdate:
                self.vcs.vcsUpdate(self.projectDir, True)
                continue    # check again
                self.shouldUpdate = False
            
            # wait until interval has expired checking for a stop condition
            self.monitorMutex.lock()
            if not self.__stopIt:
                self.monitorCondition.wait(
                    self.monitorMutex, self.interval * 1000)
            self.monitorMutex.unlock()
        
        self._shutdown()
        self.exit()
    
    def setInterval(self, interval):
        """
        Public method to change the monitor interval.
        
        @param interval new interval in seconds (integer)
        """
        locked = self.monitorMutex.tryLock()
        self.interval = interval
        self.monitorCondition.wakeAll()
        if locked:
            self.monitorMutex.unlock()
    
    def getInterval(self):
        """
        Public method to get the monitor interval.
        
        @return interval in seconds (integer)
        """
        return self.interval
    
    def setAutoUpdate(self, auto):
        """
        Public method to enable the auto update function.
        
        @param auto status of the auto update function (boolean)
        """
        self.autoUpdate = auto
    
    def getAutoUpdate(self):
        """
        Public method to retrieve the status of the auto update function.
        
        @return status of the auto update function (boolean)
        """
        return self.autoUpdate
    
    def checkStatus(self):
        """
        Public method to wake up the status monitor thread.
        """
        locked = self.monitorMutex.tryLock()
        self.monitorCondition.wakeAll()
        if locked:
            self.monitorMutex.unlock()
    
    def stop(self):
        """
        Public method to stop the monitor thread.
        """
        locked = self.monitorMutex.tryLock()
        self.__stopIt = True
        self.monitorCondition.wakeAll()
        if locked:
            self.monitorMutex.unlock()

    def clearCachedState(self, name):
        """
        Public method to clear the cached VCS state of a file/directory.
        
        @param name name of the entry to be cleared (string)
        """
        key = self.project.getRelativePath(name)
        try:
            del self.reportedStates[key]
        except KeyError:
            pass

    def _performMonitor(self):
        """
        Protected method implementing the real monitoring action.
        
        This method must be overridden and populate the statusList member
        variable with a list of strings giving the status in the first column
        and the path relative to the project directory starting with the
        third column. The allowed status flags are:
        <ul>
            <li>"A" path was added but not yet comitted</li>
            <li>"M" path has local changes</li>
            <li>"O" path was removed</li>
            <li>"R" path was deleted and then re-added</li>
            <li>"U" path needs an update</li>
            <li>"Z" path contains a conflict</li>
            <li>" " path is back at normal</li>
        </ul>
        
        @ireturn tuple of flag indicating successful operation (boolean) and
            a status message in case of non successful operation (string)
        @exception RuntimeError to indicate that this method must be
            implemented by a subclass
        """
        raise RuntimeError('Not implemented')
    
    def _shutdown(self):
        """
        Protected method performing shutdown actions.
        
        The default implementation does nothing.
        """
        pass
Ejemplo n.º 25
0
class ValueLabelGui(QWidget):
    
    start_signal = QtCore.pyqtSignal()
    stop_signal = QtCore.pyqtSignal()
    
    def __init__(self, parent=None, window=None, devicewrapper=None):
        """ """
        super(ValueLabelGui, self).__init__(parent=parent)
        self._init_ui(window)
        self._init_worker_thread(devicewrapper)
        
    
    def _init_ui(self, mainwindow):

        self.central_wid = QWidget(mainwindow)
        self._set_central_wid_properties()
        self.mainwindow = mainwindow
        self.mainwindow.setCentralWidget(self.central_wid)  
        
        

        # grid layout to put all widgets
        self.wid_layout = QGridLayout()
           
        
        # =====================================================================
        # control panel
        # =====================================================================
        self.graphics_layout = QGridLayout()
        self.vl = pg.ValueLabel(formatStr='{avgValue:0.2f} {suffix}')
        self.vl.setValue(-1)
        self.graphics_layout.addWidget(self.vl, 0, 0, 4, 4)
        
        
        # =====================================================================
        # control panel
        # =====================================================================
        self.controls_layout = QGridLayout()


        # =====================================================================
        # control buttons - layout
        # =====================================================================
        self.startBtn = QPushButton('START')
        self.controls_layout.addWidget(self.startBtn, 0, 0, 1, 1)
        self.stopBtn = QPushButton('STOP')
        self.controls_layout.addWidget(self.stopBtn, 1, 0, 1, 1)
        
        
        # =====================================================================
        # control buttons - connections
        # =====================================================================
        self.startBtn.clicked.connect(self.start_thread)
        self.stopBtn.clicked.connect(self.stop_thread)

       # ============================================================
        # put everything together
        # ============================================================
        self.wid_layout.addItem(self.graphics_layout, 0, 0, 2, 2)
        self.wid_layout.addItem(self.controls_layout, 0, 2, 2, 2)     
        # self.wid_layout.setColumnStretch(0, 10)
        # self.wid_layout.setColumnStretch(8, 2)
        
        self.central_wid.setLayout(self.wid_layout)


    def _set_central_wid_properties(self):
        """ """
        self.central_wid.setAutoFillBackground(True)
        p = self.central_wid.palette()
        p.setColor(self.central_wid.backgroundRole(), QtCore.Qt.darkGray)
        self.central_wid.setPalette(p)    
        
  
    def _init_worker_thread(self, devicewrapper):
        """ """
        
        # Setup QWaitCondition
        self.mutex = QMutex()
        self.cond = QWaitCondition()
        
        # Setup the measurement engine        
#        self.mthread = QtCore.QThread()
        self.worker = TimePlotWorker(devicewrapper, self.mutex, self.cond)        
        
        
        # connect signal and slots
        self.start_signal.connect(self.worker.start)
        self.stop_signal.connect(self.worker.stop)
        
        
        self.worker.reading.connect(self.newReading)
        
        return


    def start_thread(self):
        self.start_signal.emit()
        
    def stop_thread(self):
        self.stop_signal.emit()
        
    def update_ValueLabel(self, val):
        """ """
        self.vl.setValue(val)
        


    @QtCore.pyqtSlot(float)
    def newReading(self, val):
        """ """
        pg.QtGui.QApplication.processEvents()
        
        self.update_ValueLabel(val)
        time.sleep(0.1)         # necessary to avoid worker to freeze
        self.cond.wakeAll()     # wake worker thread up 
        return



    def closeEvent(self, event):
        reply = QMessageBox.question(self, 'Message',
            "Are you sure to quit?", QMessageBox.Yes | 
            QMessageBox.No, QMessageBox.Yes)

        if reply == QMessageBox.Yes:
            event.accept()
        else:
            event.ignore()  
Ejemplo n.º 26
0
class MyWidget(QWidget):

    def __init__(self):
        super(MyWidget, self).__init__()

        self.cur_path = os.path.split(os.path.realpath(__file__))[0]
        self.im_original = None
        self.mutex = QMutex()
        self.condition = QWaitCondition()
        self.cam_thread = CamThread(mutex=self.mutex, condition=self.condition)
        self.cam_thread.signal_im_ready.connect(self.set_im)
        self.cam_thread.signal_original_im_ready.connect(self.set_original_im)

        self.x0 = 0
        self.y0 = 0
        self.x1 = 0
        self.y1 = 0
        self.is_moving = False
        self.is_resizing = False

        self.is_capture = False
        self.confidence = 0.5

        """ controls """
        # layout
        self.hbox_main = QHBoxLayout(self)
        self.vbox_btns = QVBoxLayout(self)
        self.vbox_im = QHBoxLayout(self)
        self.hbox_who = QHBoxLayout(self)

        # button
        self.btn_save_image = QPushButton('Save Image', self)
        self.btn_train = QPushButton('Train', self)
        self.btn_load_image = QPushButton('Load Image \n And Recognize', self)
        self.btn_start_camera = QPushButton('Start Camera', self)
        self.btn_stop_camera = QPushButton('Stop Camera', self)
        self.btn_test = QPushButton('Test', self)

        size_policy = QSizePolicy(QSizePolicy.Expanding, QSizePolicy.Expanding)
        self.btn_save_image.setSizePolicy(size_policy)
        self.btn_train.setSizePolicy(size_policy)
        self.btn_load_image.setSizePolicy(size_policy)
        self.btn_start_camera.setSizePolicy(size_policy)
        self.btn_stop_camera.setSizePolicy(size_policy)
        self.btn_test.setSizePolicy(size_policy)

        # line text
        self.txb_who = QLineEdit("", self)

        # label
        self.lb_realtime = QLabel("", self)
        self.lb_template = QLabel("", self)
        self.lb_result = QLabel("", self)
        self.lb_who = QLabel('Who:', self)

        """ place controls to layout """
        self.hbox_who.addWidget(self.lb_who)
        self.hbox_who.addWidget(self.txb_who)

        self.vbox_im.addWidget(self.lb_realtime, alignment=Qt.AlignTop)

        self.vbox_btns.addLayout(self.hbox_who)
        self.vbox_btns.addWidget(self.btn_save_image)
        self.vbox_btns.addWidget(self.btn_train)
        self.vbox_btns.addWidget(self.btn_load_image)
        self.vbox_btns.addWidget(self.btn_start_camera)
        self.vbox_btns.addWidget(self.btn_stop_camera)
        self.vbox_btns.addWidget(self.btn_test)

        self.hbox_main.addLayout(self.vbox_im)
        self.hbox_main.addLayout(self.vbox_btns)
        self.hbox_main.addWidget(self.lb_template, alignment=Qt.AlignHCenter)
        self.hbox_main.addWidget(self.lb_result, alignment=Qt.AlignHCenter)

        self.setLayout(self.hbox_main)

        """ connect signal and slot """
        self.btn_save_image.clicked.connect(self.on_btn_save_image_clicked)
        self.btn_train.clicked.connect(self.on_btn_train_clicked)
        self.btn_load_image.clicked.connect(self.on_btn_load_image_clicked)
        self.btn_start_camera.clicked.connect(self.on_btn_start_camera_clicked)
        self.btn_stop_camera.clicked.connect(self.on_btn_stop_camera_clicked)
        self.btn_test.clicked.connect(self.on_btn_test_clicked)

        self.lb_realtime.mousePressEvent = self.on_lb_realtime_mouse_press
        self.lb_realtime.mouseMoveEvent = self.on_lb_realtime_mouse_move
        self.lb_realtime.mouseReleaseEvent = self.on_lb_realtime_mouse_release

        self.setWindowTitle('qt face recognition')
        self.show()

        self.btn_test.setVisible(False)

    @pyqtSlot('QImage')
    def set_im(self, image):
        self.mutex.lock()
        try:
            self.lb_realtime.setPixmap(QPixmap.fromImage(image))
        finally:
            self.mutex.unlock()
            self.condition.wakeAll()

    @pyqtSlot(object)
    def set_original_im(self, cv_im):
        self.im_original = cv_im

    def on_lb_realtime_mouse_move(self, event):
        try:

            is_moving = True
            self.x1 = event.x()
            self.y1 = event.y()
            self.cam_thread.updateDrawingData(self.x0,
                                              self.y0,
                                              self.x1,
                                              self.y1,
                                              is_moving)

        except Exception as e:
            print(e)

    def on_lb_realtime_mouse_press(self, event):
        try:
            self.is_moving = False
            self.x0 = event.x()
            self.y0 = event.y()

            self.cam_thread.updateDrawingData(self.x0,
                                              self.y0,
                                              self.x1,
                                              self.y1,
                                              self.is_moving)
        except Exception as e:
            print(e)

    def on_lb_realtime_mouse_release(self, event):
        pass

    def closeEvent(self, event):
        print("[INFO] closed")
        self.cam_thread.update_is_capture(False)
        event.accept()

    def on_btn_load_image_clicked(self, _):
        self.load_image_and_recognize()

    def on_btn_save_image_clicked(self, _):
        if self.is_capture:
            self.save_image()
        else:
            print("[INFO] please start camera first")

    def on_btn_train_clicked(self, _):
        self.is_capture = False
        self.cam_thread.update_is_capture(self.is_capture)

        self.train()

    def on_btn_start_camera_clicked(self, _):
        if not self.is_capture:
            self.mutex.lock()

            self.is_capture = True
            self.cam_thread.update_is_capture(self.is_capture)

            self.cam_thread.my_face_recognizer.load_face_recognize_models()
            self.cam_thread.my_face_recognizer.load_face_detect_model()

            self.cam_thread.start()

    def on_btn_stop_camera_clicked(self, _):
        self.is_capture = False
        self.cam_thread.update_is_capture(self.is_capture)

    def on_btn_test_clicked(self, _):
        # self.cam_thread.my_face_recognizer.load_face_detect_model()
        # self.cam_thread.my_face_recognizer.load_face_recognize_models()
        pass

    def load_image_and_recognize(self):
        try:
            filter_by = "Image files (*.jpg *.jpeg *.png *.bmp *.tif *.tiff)"

            fname = QFileDialog.getOpenFileName(self,
                                                "Open file",
                                                os.getcwd(),
                                                filter_by)[0]

            if not fname == "":

                img = cv2.imread(fname, cv2.IMREAD_COLOR)
                img = imutils.resize(img, width=600)
                (h, w) = img.shape[:2]

                image_blob = cv2.dnn.blobFromImage(
                    cv2.resize(img, (300, 300)), 1.0, (300, 300),
                    (104.0, 177.0, 123.0), swapRB=False, crop=False)

                face_recognizer = FaceRecognizer()
                face_recognizer.load_face_recognize_models()
                face_recognizer.load_face_detect_model()

                detected_faces = face_recognizer.detect_faces(image_blob)
                index_face = 0
                confidence = detected_faces[0, 0, index_face, 2]

                if confidence > face_recognizer.get_min_confidence():
                    box = detected_faces[0, 0, index_face, 3:7] * np.array([w, h, w, h])
                    (startX, startY, endX, endY) = box.astype("int")

                    # extract the face ROI
                    face = img[startY:endY, startX:endX]
                    # (fH, fW) = face.shape[:2]

                    # # ensure the face width and height are sufficiently large
                    # if fW < 20 or fH < 20:
                    #    continue

                    face_blob = cv2.dnn.blobFromImage(face,
                                                      1.0 / 255,
                                                      (96, 96),
                                                      (0, 0, 0),
                                                      swapRB=True,
                                                      crop=False)

                    name, proba = face_recognizer.predict_name(face_blob)
                    self.txb_who.setText(name)

                    # draw the bounding box and probability
                    text = "{}: {:.2f}%".format(name, proba * 100)
                    y = startY - 10 if startY - 10 > 10 else startY + 10

                    img = cv2.cvtColor(img,
                                       cv2.COLOR_BGR2RGB)

                    cv2.rectangle(img, (startX, startY), (endX, endY),
                                  (255, 0, 0), 2)
                    cv2.putText(img, text, (startX, y),
                                cv2.FONT_HERSHEY_SIMPLEX, 0.45,
                                (255, 0, 0), 2)
                else:
                    img = cv2.cvtColor(img, cv2.COLOR_BGR2RGB)

                q_img = QImage(img.data,
                               img.shape[1],
                               img.shape[0],
                               QImage.Format_RGB888)
                q_img = q_img.scaled(640, 480,
                                     Qt.KeepAspectRatio)

                self.lb_realtime.setPixmap(QPixmap.fromImage(q_img))
                self.lb_realtime.update()
        except Exception as e:
            print(e)

    def save_image(self):

        folder_path = self.cur_path + '/face_recognition_dataset/' + self.txb_who.text()
        if not os.path.exists(folder_path):
            os.makedirs(folder_path)

        num_images = 0
        for (dirpath, dirnames, filenames) in walk(folder_path):
            for filename in filenames:
                filetype = filename.split(".")[-1]
                if filetype == "jpg":
                    num_images += 1

        str_number = '{:0>5d}'.format(num_images)
        image_path = folder_path + '/' + self.txb_who.text() + str_number + '.jpg'
        cv2.imwrite(image_path, self.im_original)
        print("[INFO] saved " + image_path)

    def train(self):
        self.cam_thread.my_face_recognizer.train_with_bo()
Ejemplo n.º 27
0
class VcsStatusMonitorThread(QThread):
    """
    Class implementing the VCS status monitor thread base class.
    
    @signal vcsStatusMonitorData(list of str) emitted to update the VCS status
    @signal vcsStatusMonitorStatus(str, str) emitted to signal the status of
        the monitoring thread (ok, nok, op) and a status message
    @signal vcsStatusMonitorInfo(str) emitted to signal some info of the
        monitoring thread
    """
    vcsStatusMonitorData = pyqtSignal(list)
    vcsStatusMonitorStatus = pyqtSignal(str, str)
    vcsStatusMonitorInfo = pyqtSignal(str)

    def __init__(self, interval, project, vcs, parent=None):
        """
        Constructor
        
        @param interval new interval in seconds (integer)
        @param project reference to the project object (Project)
        @param vcs reference to the version control object
        @param parent reference to the parent object (QObject)
        """
        super(VcsStatusMonitorThread, self).__init__(parent)
        self.setObjectName("VcsStatusMonitorThread")

        self.setTerminationEnabled(True)

        self.projectDir = project.getProjectPath()
        self.project = project
        self.vcs = vcs

        self.interval = interval
        self.autoUpdate = False

        self.statusList = []
        self.reportedStates = {}
        self.shouldUpdate = False

        self.monitorMutex = QMutex()
        self.monitorCondition = QWaitCondition()
        self.__stopIt = False

    def run(self):
        """
        Public method implementing the tasks action.
        """
        while not self.__stopIt:
            # perform the checking task
            self.statusList = []
            self.vcsStatusMonitorStatus.emit(
                "wait",
                QCoreApplication.translate("VcsStatusMonitorThread",
                                           "Waiting for lock"))
            try:
                locked = self.vcs.vcsExecutionMutex.tryLock(5000)
            except TypeError:
                locked = self.vcs.vcsExecutionMutex.tryLock()
            if locked:
                try:
                    self.vcsStatusMonitorStatus.emit(
                        "op",
                        QCoreApplication.translate(
                            "VcsStatusMonitorThread",
                            "Checking repository status"))
                    res, statusMsg = self._performMonitor()
                    infoMsg = self._getInfo()
                finally:
                    self.vcs.vcsExecutionMutex.unlock()
                if res:
                    status = "ok"
                else:
                    status = "nok"
                self.vcsStatusMonitorStatus.emit(
                    "send",
                    QCoreApplication.translate("VcsStatusMonitorThread",
                                               "Sending data"))
                self.vcsStatusMonitorData.emit(self.statusList)
                self.vcsStatusMonitorStatus.emit(status, statusMsg)
                self.vcsStatusMonitorInfo.emit(infoMsg)
            else:
                self.vcsStatusMonitorStatus.emit(
                    "timeout",
                    QCoreApplication.translate("VcsStatusMonitorThread",
                                               "Timed out waiting for lock"))
                self.vcsStatusMonitorInfo.emit("")

            if self.autoUpdate and self.shouldUpdate:
                self.vcs.vcsUpdate(self.projectDir, True)
                continue  # check again
                self.shouldUpdate = False

            # wait until interval has expired checking for a stop condition
            self.monitorMutex.lock()
            if not self.__stopIt:
                self.monitorCondition.wait(self.monitorMutex,
                                           self.interval * 1000)
            self.monitorMutex.unlock()

        self._shutdown()
        self.exit()

    def setInterval(self, interval):
        """
        Public method to change the monitor interval.
        
        @param interval new interval in seconds (integer)
        """
        locked = self.monitorMutex.tryLock()
        self.interval = interval
        self.monitorCondition.wakeAll()
        if locked:
            self.monitorMutex.unlock()

    def getInterval(self):
        """
        Public method to get the monitor interval.
        
        @return interval in seconds (integer)
        """
        return self.interval

    def setAutoUpdate(self, auto):
        """
        Public method to enable the auto update function.
        
        @param auto status of the auto update function (boolean)
        """
        self.autoUpdate = auto

    def getAutoUpdate(self):
        """
        Public method to retrieve the status of the auto update function.
        
        @return status of the auto update function (boolean)
        """
        return self.autoUpdate

    def checkStatus(self):
        """
        Public method to wake up the status monitor thread.
        """
        locked = self.monitorMutex.tryLock()
        self.monitorCondition.wakeAll()
        if locked:
            self.monitorMutex.unlock()

    def stop(self):
        """
        Public method to stop the monitor thread.
        """
        locked = self.monitorMutex.tryLock()
        self.__stopIt = True
        self.monitorCondition.wakeAll()
        if locked:
            self.monitorMutex.unlock()

    def clearCachedState(self, name):
        """
        Public method to clear the cached VCS state of a file/directory.
        
        @param name name of the entry to be cleared (string)
        """
        key = self.project.getRelativePath(name)
        try:
            del self.reportedStates[key]
        except KeyError:
            pass

    def _performMonitor(self):
        """
        Protected method implementing the real monitoring action.
        
        This method must be overridden and populate the statusList member
        variable with a list of strings giving the status in the first column
        and the path relative to the project directory starting with the
        third column. The allowed status flags are:
        <ul>
            <li>"A" path was added but not yet comitted</li>
            <li>"M" path has local changes</li>
            <li>"O" path was removed</li>
            <li>"R" path was deleted and then re-added</li>
            <li>"U" path needs an update</li>
            <li>"Z" path contains a conflict</li>
            <li>" " path is back at normal</li>
        </ul>
        
        @return tuple of flag indicating successful operation (boolean) and
            a status message in case of non successful operation (string)
        @exception RuntimeError to indicate that this method must be
            implemented by a subclass
        """
        raise RuntimeError('Not implemented')

        return ()

    def _getInfo(self):
        """
        Protected method implementing the real info action.
        
        This method should be overridden and create a short info message to be
        shown in the main window status bar right next to the status indicator.
        
        @return short info message
        @rtype str
        """
        return ""

    def _shutdown(self):
        """
        Protected method performing shutdown actions.
        
        The default implementation does nothing.
        """
        pass
Ejemplo n.º 28
0
class Thread(QThread):
    """The downloading is handled in a separate thread in order for the progress bar and the pause button to work"""
    change_value = pyqtSignal(int)
    done = pyqtSignal(int)
    log = pyqtSignal(str)
    is_cancelled = False
    done_cards = []

    def __init__(self, cards, mw, config):
        QThread.__init__(self)
        self.cond = QWaitCondition()
        self.mutex = QMutex()
        self.cnt = 0
        self._status = True
        self.cards = cards
        self.mw = mw
        self.skipped_cards = 0
        self.failed: List[FailedDownload] = []
        self.config: Config = config

    def __del__(self):
        self.wait()

    def run(self):
        from . import log_dir

        skip_existing = self.config.get_config_object(
            "skipExistingBulkAdd").value

        card: Card
        for card in self.cards:
            """Go through all cards that are selected in the editor"""
            # self.mutex.lock()
            if self.is_cancelled:
                Forvo.cleanup()
                return
            if not self._status:  # If download is paused, wait
                self.cond.wait(self.mutex)
            try:  # use try to avoid stopping the entire thread because of a single exception
                # Get fields from config

                query_field = self.config.get_note_type_specific_config_object(
                    "searchField",
                    card.note_type()["id"]).value
                audio_field = self.config.get_note_type_specific_config_object(
                    "audioField",
                    card.note_type()["id"]).value

                if query_field not in card.note():
                    raise FieldNotFoundException(query_field)

                if audio_field not in card.note():
                    raise FieldNotFoundException(audio_field)

                query = card.note(
                )[query_field]  # Get query string from card's note using field name
                language = self.config.get_deck_specific_config_object(
                    "language", card.did).value

                self.log.emit("[Next Card] Query: %s; Language: %s" %
                              (query, language))

                if skip_existing and len(card.note()[audio_field]) > 0:
                    """Skip cards that already have something in the audio field if the setting is turned on"""
                    self.skipped_cards += 1
                    continue

                # Get language from config for the card's deck

                # Get the results
                results = Forvo(query, language, self.mw) \
                    .load_search_query() \
                    .get_pronunciations().pronunciations

                results.sort(key=lambda result: result.votes)  # sort by votes

                top: Pronunciation = results[
                    len(results) - 1]  # get most upvoted pronunciation
                self.log.emit("Selected pronunciation by %s with %s votes" %
                              (top.user, str(top.votes)))
                top.download_pronunciation()  # download that
                self.log.emit("Downloaded pronunciation")
                if self.config.get_config_object("appendAudio").value:
                    card.note(
                    )[audio_field] += "[sound:%s]" % top.audio  # set audio field content to the respective sound
                    self.log.emit("Appended sound string to field content")
                else:
                    card.note(
                    )[audio_field] = "[sound:%s]" % top.audio  # set audio field content to the respective sound
                    self.log.emit("Placed sound string in field")

                card.note().flush()  # flush the toilet
                self.log.emit("Saved note")
            except Exception as e:
                # Save all raised exceptions in a list to retrieve them later in the FailedDownloadsDialog
                self.failed.append(FailedDownload(reason=e, card=card))
                self.log.emit(
                    "[Error] Card with 1. Field %s failed due to Exception: %s"
                    % (card.note().fields[0], str(e)))
                with open(os.path.join(
                        log_dir, "bulk_error_log-" +
                        datetime.now().strftime('%Y-%m-%dT%H') + ".log"),
                          "a",
                          encoding="utf8") as f:
                    f.write("\n".join(
                        traceback.format_exception(None, e, e.__traceback__)) +
                            "\n------------------\n")

            self.done_cards.append(card)
            self.cnt += 1  # Increase count for progress bar
            self.change_value.emit(
                self.cnt)  # emit signal to update progress bar
            self.msleep(1000)  # sleep to give progress bar time to update

            # self.mutex.unlock()

        Forvo.cleanup(
        )  # cleanup files in temp directory (None is passed as the self parameter here)

    def toggle_status(self):  # toggle pause state
        self._status = not self._status
        if self._status:
            self.cond.wakeAll()

    @property
    def status(self):
        return self._status
Ejemplo n.º 29
0
class CollectToMySQLThread(QThread):
    def __init__(self, config, market='SH'):
        super(self.__class__, self).__init__()
        self.working = True
        self._config = config
        self.market = market.lower()
        self.marketid = None
        assert config.getboolean("mysql", "enable", fallback=False)
        self._db_config = {
            'user': config['mysql']['usr'],
            'password': config['mysql']['pwd'],
            'host': config['mysql']['host'],
            'port': config['mysql']['port']
        }
        self._connect = None
        self.quotations = [
            'stock',
        ]  # sina 不支持基金,qq支持,此处屏蔽基金
        #if config['quotation']['stock']:
        #    self.quotations.append('stock')
        #if config['quotation']['fund']:
        #    self.quotations.append('fund')
        #self.logger.info(self.quotations)

        self._interval = TimeDelta(
            seconds=config.getint('collect', 'interval', fallback=60 * 60))
        self._phase1_start_time = Datetime(
            datetime.datetime.combine(
                datetime.date.today(),
                datetime.time.fromisoformat((config.get('collect',
                                                        'phase1_start',
                                                        fallback='09:05')))))
        self._phase1_end_time = Datetime(
            datetime.datetime.combine(
                datetime.date.today(),
                datetime.time.fromisoformat((config.get('collect',
                                                        'phase1_end',
                                                        fallback='09:05')))))
        self._use_zhima_proxy = config.getboolean('collect',
                                                  'use_zhima_proxy',
                                                  fallback=False)

        self.cond = QWaitCondition()
        self.mutex = QMutex()

    def stop(self):
        if self.working:
            self.working = False
            self.cond.wakeAll()
            self.wait()
            if self._connect is not None:
                hku_trace('关闭数据库连接', logger=self.logger)
                self._connect.close()

    def __del__(self):
        self.stop()

    @hku_catch()
    def run(self):
        self.logger.info("{} 数据采集同步线程启动".format(self.market))
        stk_list = self.get_stock_list()
        hku_warn_if(not stk_list, "从数据库中获取的股票列表为空!", logger=self.logger)
        self.mutex.tryLock()

        end_delta = self._phase1_end_time - self._phase1_end_time.start_of_day(
        )
        start_delta = self._phase1_start_time - self._phase1_start_time.start_of_day(
        )

        start = Datetime.now()
        if self._phase1_start_time >= self._phase1_end_time:
            delta = TimeDelta(0)
        elif start >= self._phase1_end_time:
            delta = (self._phase1_start_time + TimeDelta(1) - start)
        elif start < self._phase1_start_time:
            delta = (self._phase1_start_time - start)
        else:
            delta = self._interval * ceil(
                (start - self._phase1_start_time) / self._interval) - (
                    start - self._phase1_start_time)

        hku_info('{} 下次采集时间:{}',
                 self.market,
                 start + delta,
                 logger=self.logger)
        delta = int(delta.total_milliseconds())
        while self.working and not self.cond.wait(self.mutex, int(delta)):
            last_time = Datetime.today() + end_delta
            start = Datetime.now()
            if start >= last_time:
                next_time = Datetime.today() + TimeDelta(1) + start_delta
                hku_info('{} 明日采集时间:{}',
                         self.market,
                         next_time,
                         logger=self.logger)
                delta = next_time - start
                delta = int(delta.total_milliseconds())
                continue
            hku_trace("start:{}".format(start))
            self.collect(stk_list)
            end = Datetime.now()
            x = end - start
            if x + TimeDelta(seconds=1) < self._interval:
                delta = self._interval - x - TimeDelta(seconds=1)
                delta = int(delta.total_milliseconds())
                self.logger.info("{} {:<.2f} 秒后重新采集".format(
                    self.market, delta / 1000))
                #self.sleep(delta)

        self.logger.info("{} 数据采集同步线程终止!".format(self.market))

    def record_is_valid(self, record):
        return record['amount'] > 0.0 and record['volumn'] > 0.0 \
            and record['high'] >= record['open'] >= record['low'] > 0.0 \
            and record['high'] >= record['close'] >= record['low']

    @hku_catch(ret=False)
    def process_one_record(self, record):
        if not self.record_is_valid(record):
            return (0, 0)
        connect = self.get_connect()
        current_date = Datetime(record['datetime'].date()).number
        table = get_table(connect, self.market, record['code'], 'day')
        sql = 'replace into {} (date, open, high, low, close, amount, count) \
             values ({}, {}, {}, {}, {}, {}, {})'.format(
            table, current_date, record['open'], record['high'], record['low'],
            record['close'], record['amount'], record['volumn'])
        cur = connect.cursor()
        cur.execute(sql)
        cur.close()
        return

    @hku_catch()
    def collect(self, stk_list):
        record_list = get_spot_parallel(stk_list,
                                        source='sina',
                                        use_proxy=self._use_zhima_proxy)
        hku_info("{} 网络获取数量:{}".format(self.market, len(record_list)))
        connect = self.get_connect()
        if self.marketid == None:
            self.marketid = get_marketid(connect, self.market)
        update_count = 0
        for record in record_list:
            if not self.working:
                break
            if self.process_one_record(record):
                update_count += 1
        connect.commit()
        hku_info("{} 数据库更新记录数:{}".format(self.market, update_count))

    def get_connect(self):
        if self._connect:
            return self._connect
        try:
            self._connect = mysql.connector.connect(**self._db_config)
        except mysql.connector.Error as err:
            if err.errno == errorcode.ER_ACCESS_DENIED_ERROR:
                self.logger.error("MYSQL密码或用户名错误!")
            elif err.errno == errorcode.ER_BAD_DB_ERROR:
                self.logger.error("MySQL数据库不存在!")
            else:
                self.logger.error("连接数据库失败,{}".format(err.msg))
        except:
            self.logger.error("未知原因导致无法连接数据库!")
        return self._connect

    @hku_catch(retry=2, ret=[])
    def get_stock_list(self):
        connect = self.get_connect()
        stk_list = get_stock_list(connect, self.market, self.quotations)
        return [
            "{}{}".format(self.market.lower(), item[2]) for item in stk_list
            if item[3] == 1
        ]
Ejemplo n.º 30
0
class FileConverter(QThread):
    progress_signal = pyqtSignal(int, int)
    conversion_status_signal = pyqtSignal(str, int, int)
    file_converted_signal = pyqtSignal()
    conversion_complete = pyqtSignal()
    ask_overwrite_signal = pyqtSignal(str)

    def __init__(self, data_file_container, parameters):
        # parameters is a dict of parameters required by FileConverter
        super().__init__()
        self.mutex = QMutex()
        self.wait_condition = QWaitCondition()
        self.data_file_container = data_file_container
        self.parameters = parameters
        self.current_file_ind = 0
        self.file_sizes = [file.size if file.status == 'unconverted' else 0
                           for file in data_file_container]
        self.unconverted_files = self.data_file_container.unconverted()
        self.total_mb = sum(self.file_sizes)
        self._is_running = False
        self.converter = None
        self.overwrite = None

    def run(self):
        self._is_running = True
        count = 0
        for i, file in enumerate(self.data_file_container):
            if not self._is_running:
                break
            if file.status != 'unconverted':
                continue
            count += 1
            self.current_file_ind = i
            self.conversion_status_signal.emit(
                file.filename, count, self.unconverted_files)
            # if not os.path.isfile(file.path):
            #     file.status = 'not found'
            #     continue
            self._convert_file(file)
            self.file_converted_signal.emit()
        self.conversion_complete.emit()

    def _convert_file(self, file):
        self.current_file = file
        try:
            conversion_parameters = default_parameters()
            conversion_parameters.update(self.parameters)
            conversion_parameters['overwrite'] = self._process_overwrite()
            self.converter = DataConverter(file.path, conversion_parameters)
            self.converter.register_observer(self.update_progress)
            self.converter.convert()
            self.data_file_container.change_status(file, 'converted')
        except FileExistsError as message:
            self.ask_overwrite(file.filename)
            if self.overwrite in ['once', 'yes_to_all']:
                self._convert_file(file)
        except (TypeError, ValueError, IndexError) as m:
            if str(m) == 'Not all required sensors present':
                self.data_file_container.change_status(
                    file, 'error_sensor_missing')
            else:
                self.data_file_container.change_status(file, 'error_failed')
        except FileNotFoundError:
            self.data_file_container.change_status(file, 'error_missing')
        except NoDataError:
            self.data_file_container.change_status(file, 'error_no_data')
        finally:
            self.converter.close_source()

        # check for the case that the conversion was canceled
        if not self.converter._is_running:
            self.data_file_container.change_status(file, 'unconverted')

    def update_progress(self, percent_done):
        # This is an observer function that gets notified when a data
        # page is parsed
        if not self._is_running:
            self.converter.cancel_conversion()
        cumulative_mb = sum([size for size
                             in self.file_sizes[:self.current_file_ind]])
        cumulative_mb += (self.data_file_container[self.current_file_ind].size
                          * (percent_done/100))
        overall_percent = cumulative_mb / self.total_mb
        overall_percent *= 100
        self.progress_signal.emit(percent_done, overall_percent)

    def _process_overwrite(self):
        # TODO why is there a tuple used below when index 0 isn't used?
        action_map = {
            'once': (None, True),
            'yes_to_all': ('yes_to_all', True),
            'no': (None, False),
            'no_to_all': ('no_to_all', False)
        }
        _, overwrite_status = action_map.get(self.overwrite, (None, False))
        return overwrite_status

    def ask_overwrite(self, filename):
        if self.overwrite is None:
            self.ask_overwrite_signal.emit(str(filename))
            self.mutex.lock()
            self.wait_condition.wait(self.mutex)
            self.mutex.unlock()

    def set_overwrite(self, state):
        self.overwrite = state
        self.wait_condition.wakeAll()

    def cancel(self):
        self._is_running = False
Ejemplo n.º 31
0
class LogThread(QThread):
    exeCnt = 0
    logTreeFinished = pyqtSignal(dict, int, str)
    logViewFinished = pyqtSignal(dict, int)

    def __init__(self, ip, tp):
        QThread.__init__(self)
        self.cond = None
        self.mutex = None
        self._status = True
        self.ip = ip
        self.tp = tp
        self.guid = ''
        self.icnt = 0
        self.tot_cnt = 0
        self.max_line = 8000

    def __del__(self):
        self.wait()

    def run(self):
        log_tree = {}
        tot_line_cnt = 0
        guid = ''

        self.cond = QWaitCondition()
        self.mutex = QMutex()
        self.mutex.lock()

        # self.msleep(100)
        if not self._status:
            self.cond.wait(self.mutex)

        try:
            swgs_url = 'http://172.31.196.21:8060/websquare/Service/SVC?commonsvc=0&rtcode=0&Trx_code=ZORDSCOM06020_TR01&ScreenName=ZORDSCOM06020&fCloseAccount=0&LogLvlGbn=&G_BizCd=null&G_Biz_Start_Time=null&__smReqSeq=5&_useLayout=true'
            payload = {"input1": [{"fcnt": "0", "flag": "T", "guid": self.guid, "icnt": self.icnt, "ip_addr": self.ip, "rowStatus": "C", "tp_id": self.tp, "prod_skip": "N"}],
                         "HEAD":  {"Trx_Code": "ZORDSCOM06020_TR01",
                                   "Ngms_UserId": "1000852323",
                                   "Ngms_LogInId": "ENJOYHAN",
                                   "Ngms_EmpNum": "",
                                   "Ngms_OrgId": "A000700000",
                                   "Ngms_HrOrgCd": "",
                                   "Ngms_PostOrgCd": "A000700000",
                                   "Ngms_PostSaleOrgCd": "A000700000",
                                   "Ngms_SupSaleOrgCd": "A010890000",
                                   "Ngms_IpAddr": "150.28.65.76",
                                   "Ngms_BrTypCd": "450",
                                   "Ngms_AuthId": "",
                                   "Ngms_ConnOrgId": "A000700000",
                                   "Ngms_ConnOrgCd": "A000700000",
                                   "Ngms_ConnSaleOrgId": "A000700000",
                                   "Ngms_ConnSaleOrgCd": "A000700000",
                                   "Ngms_AuthTypPermCd": "EQ",
                                   "Ngms_PostSaleOrgId": "A000700000",
                                   "Ngms_SupSaleOrgId": "A010890000",
                                   "Term_Type": "0",
                                   "User_Term_Type": "",
                                   "St_Stop": "0",
                                   "St_Trace": "",
                                   "Stx_Dt": "",
                                   "Stx_Tm": "",
                                   "Etx_Dt": "",
                                   "Etx_Tm": "",
                                   "Rt_Cd": "",
                                   "Screen_Name": "ZORDSCOM06020",
                                   "Msg_Cnt": "0",
                                   "Handle_Id": "863017520 ",
                                   "Ngms_Filler1": "",
                                   "Ngms_CoClCd": "T",
                                   "Screen_Call_Trace": "Top-ZORDSCOM06020-ZORDSCOM06020_TR01",
                                   "rowStatus": "C"}}
            '''
            1. icnt 값이 0 인 경우 log tree 에 보여줄 값을 조회
            2. log view에 보여줄 상세 값을 조회
                2-1) tot_cnt 가 0 보다 크고 icnt 가 0인 경우 (최초 조회)
                2-2) rem_cnt 가 0 보다 큰 경우 (Append 하기 조회)
            '''
            if self.icnt == 0:
                log_tree_result = requests.get(swgs_url, json=payload)
                log_tree = log_tree_result.json()

                if log_tree:
                    if log_tree['output2']:
                        self.tot_line_cnt =int(log_tree['output2'][0]['total_cnt'])
                        self.guid = log_tree['output2'][0]['guid']

                        cnt = divmod(int(self.tot_line_cnt), int(self.max_line))
                        self.tot_cnt = cnt[0] + 1

                self.logTreeFinished.emit(log_tree, self.tot_cnt, self.guid)

            rem_cnt = self.tot_cnt - self.icnt

            if self.tot_cnt > 0 and self.icnt == 0:
                payload['input1'][0]['flag'] = 'L'
                payload['input1'][0]['guid'] = guid
                payload['input1'][0]['icnt'] = self.icnt

                log_view_result = requests.get(swgs_url, json=payload)
                log_view = log_view_result.json()

                self.icnt += 1

                self.logViewFinished.emit(log_view, self.icnt)
                print('{}번 조회완료'.format(self.icnt))
            elif rem_cnt > 0:
                log_view = {}
                for ix in range(0, rem_cnt):
                    payload['input1'][0]['flag'] = 'L'
                    payload['input1'][0]['guid'] = guid
                    payload['input1'][0]['icnt'] = self.icnt

                    log_view_result = requests.get(swgs_url, json=payload)

                    if ix == 0:
                        log_view = log_view_result.json()
                    else:
                        log_view_temp = log_view_result.json()
                        log_view['output1'].append(log_view_temp['output1'])

                    self.icnt += 1
                    print('{}번 조회완료'.format(self.icnt))

                self.logViewFinished.emit(log_view, self.icnt)
        except Exception as e:
            print(e)
        finally:
            self.mutex.unlock()

    def toggle_status(self):
        self._status = not self._status
        if self._status:
            self.cond.wakeAll()

    @property
    def status(self):
        return self._status

    def stop(self):
        self.terminate()
Ejemplo n.º 32
0
class MainWindow(QMainWindow):
    inputReceived = pyqtSignal(str)

    def __init__(self, parent=None):
        super(MainWindow, self).__init__(parent)
        self.ui = Ui_MainWindow()
        self.ui.setupUi(self)

        # Left Browser tabs
        self.ui.tabWidgetBrowser.removeTab(1)
        self.ui.tabWidgetBrowser.removeTab(1)
        self.ui.tabWidgetBrowser.setTabsClosable(True)
        self.ui.tabWidgetBrowser.tabCloseRequested.connect(self.closeBrowserTab)
        self.ui.tabWidgetBrowser.tabBarDoubleClicked.connect(lambda: self.maximizeTabs(self.ui.tabWidgetBrowser))

        # Left tree views
        self.fileTreeModel = QFileSystemModel(self)
        self.fileTreeModel.setRootPath(QDir.currentPath() + QDir.separator() + 'test')
        self.ui.treeViewFile.setModel(self.fileTreeModel)
        self.ui.treeViewFile.setRootIndex(self.fileTreeModel.index(QDir.currentPath() + QDir.separator() + 'test'))
        self.ui.treeViewFile.hideColumn(1)
        self.ui.treeViewFile.hideColumn(2)
        self.ui.treeViewFile.hideColumn(3)
        self.ui.treeViewFile.doubleClicked.connect(self.openFileFromTree)

        self.ui.treeViewFile.setAnimated(True)
        self.ui.treeViewSyntax.setAnimated(True)
        self.ui.treeViewToken.setAnimated(True)

        self.ui.treeViewFile.setHeaderHidden(True)
        self.ui.treeViewSyntax.setHeaderHidden(True)
        self.ui.treeViewToken.setHeaderHidden(True)

        # Editor tabs
        self.currentEditor = self.ui.codeEditor
        self.currentEditor.file = None
        self.currentEditorTab = self.ui.tabEditor
        self.openedEditors = [self.currentEditor]
        self.openedEditorTabs = [self.currentEditorTab]
        self.currentEditor.setFocus()  # set focus
        self.ui.tabWidgetEditor.tabCloseRequested.connect(self.closeEditorTab)
        self.ui.tabWidgetEditor.tabBarClicked.connect(self.switchEditorTab)
        self.ui.tabWidgetEditor.tabBarDoubleClicked.connect(lambda: self.maximizeTabs(self.ui.tabWidgetEditor))

        # Bottom console
        font = QFont()
        font.setFamily("Courier")
        font.setStyleHint(QFont.Monospace)
        font.setFixedPitch(True)
        font.setPointSize(10)
        self.ui.console.setFont(font)
        self.ui.console.setReadOnly(True)
        self.waitInputCond = QWaitCondition()
        self.oldConsoleText = None

        # Bottom output tabs
        self.ui.tabWidgetOutput.hide()
        self.ui.tabWidgetOutput.tabCloseRequested.connect(self.closeOutputTab)
        self.ui.tabWidgetOutput.tabBarDoubleClicked.connect(lambda: self.maximizeTabs(self.ui.tabWidgetOutput))
        self.ui.tabWidgetOutput.setTabText(0, 'Console')

        # Previous opened tabs,for maximizing
        self.preOpenedTabs = None

        # Initial size of inner splitter
        self.ui.splitterInner.setSizes([180, 459 * 2 - 180])

        # Menu "File"
        self.ui.actionOpen.triggered.connect(self.openFile)
        self.ui.actionNew.triggered.connect(self.newFile)
        self.ui.actionSave.triggered.connect(self.saveFile)
        self.ui.actionSaveAs.triggered.connect(self.saveFileAs)
        self.ui.actionQuit.triggered.connect(self.close)

        # Menu "Edit"
        self.connectMenuEditSlots()

        # Menu "View"
        self.ui.menuView.triggered.connect(self.manageMenuView)
        self.ui.actionAboutQt.triggered.connect(QApplication.aboutQt)

        # Menu "Run"
        self.ui.actionRun.triggered.connect(self.run)
        self.ui.actionBuild.triggered.connect(self.runCompile)
        self.ui.actionShowStable.triggered.connect(self.runSemantic)
        self.ui.actionRunParser.triggered.connect(self.runParser)
        self.ui.actionRunLexer.triggered.connect(self.runLexer)

    @pyqtSlot(bool)
    def runLexer(self, checked):
        """
        Run lexer and present result on self.ui.tabToken Tree
        :return:
        """
        p = self.genParser(Parser.mode_lexer)
        tokenNode = p.lexse() if p else None
        if not tokenNode:
            self.endEcho(False)
            return

        self.showBrowserTree(self.ui.tabToken, tokenNode)
        self.endEcho(True)

    @pyqtSlot(bool)
    def runParser(self, checked):
        """
        Run parser and present result on self.ui.tabSyntax Tree
        :return:
        """
        # Begin parse
        p = self.genParser(Parser.mode_parser)
        result = p.parse() if p else None
        if not result:
            self.endEcho(False)
            return

        syntaxNode, tokenNode = result

        # self.showBrowserTree(self.ui.tabToken, tokenNode)
        self.ui.treeViewToken.setModel(TreeModel(tokenNode))
        self.showBrowserTree(self.ui.tabSyntax, syntaxNode)
        self.endEcho(True)

    @pyqtSlot(bool)
    def runSemantic(self, checked):
        """
        run semantics analysing and print symbol table
        :return:
        """
        p = self.genParser(Parser.mode_stable)
        result = p.semantic() if p else None
        if not result:
            self.endEcho(False)
            return

        stable, syntaxNode, tokenNode = result

        self.ui.treeViewToken.setModel(TreeModel(tokenNode))
        self.ui.treeViewSyntax.setModel(TreeModel(syntaxNode))
        self.endEcho(True)

    @pyqtSlot(bool)
    def runCompile(self, checked):
        """
        Run compiler and print Intermediate code
        :return:
        """
        p = self.genParser(Parser.mode_compile)
        result = p.compile() if p else None
        if not result:
            self.endEcho(False)
            return

        codes, stable, syntaxNode, tokenNode = result
        self.ui.treeViewToken.setModel(TreeModel(tokenNode))
        self.ui.treeViewSyntax.setModel(TreeModel(syntaxNode))
        self.endEcho(True)

    @pyqtSlot(bool)
    def run(self, checked):
        """
        compile and run the source code

        compile in main thread and run in a worker thread
        """
        p = self.genParser(Parser.mode_execute)
        result = p.compile() if p else None
        if not result:
            self.endEcho(False)
            return

        codes, stable, syntaxNode, tokenNode = result
        self.ui.treeViewToken.setModel(TreeModel(tokenNode))
        self.ui.treeViewSyntax.setModel(TreeModel(syntaxNode))

        console = Console(self.ui.console, parent=self, waitCond=self.waitInputCond)
        console.update.connect(self.updateOutput)
        self.inputReceived.connect(console.receivedInput)
        self.ui.console.blockCountChanged.connect(self.waitInput)
        self.ui.console.textChanged.connect(self.disableBack)

        interp = Interpreter(codes, stdin=console, stdout=console, stderr=console)
        thread = ExecuteThread(interp.inter, self)
        thread.start()

    def genParser(self, mode=Parser.mode_execute):
        """
        Generate a parser instance
        :param mode:
        :return:
        """
        if not self.saveFile():
            return
        self.showOutputPanel()
        self.ui.actionViewConsole.setChecked(True)
        self.beginEcho()

        stdin = open(self.currentEditor.file, 'r')
        console = Console(self.ui.console, parent=self)
        console.update.connect(self.updateOutput)

        return Parser(stdin, stdout=console, stderr=console, mode=mode)

    def beginEcho(self):
        self.updateOutput('%s\n' % self.currentEditor.file)

    def endEcho(self, success=True):
        msg = 'successfully' if success else 'unsuccessfully'
        self.updateOutput('Process finished %s\n' % msg)

    @pyqtSlot(str)
    def updateOutput(self, content):
        """
        Update bottom text browser when content is writen to it.
        :param content:
        :return:
        """
        self.ui.console.moveCursor(QTextCursor.End)
        self.ui.console.insertPlainText('%s' % content)
        self.oldConsoleText = self.ui.console.toPlainText()

    @pyqtSlot(int)
    def waitInput(self, newBlockCount):
        """
        :param newBlockCount: line count
        :return:
        """
        if not self.ui.console.isReadOnly():
            self.inputReceived.emit(self.ui.console.toPlainText()
                                    .replace(self.oldConsoleText, ''))
            self.waitInputCond.wakeAll()
            self.ui.console.setReadOnly(True)

    @pyqtSlot()
    def disableBack(self):
        """
        disable backspace when waiting for input
        :return:
        """
        if not self.ui.console.isReadOnly():
            if len(self.oldConsoleText) > len(self.ui.console.toPlainText()):
                self.ui.console.setPlainText(self.oldConsoleText)
                self.ui.console.moveCursor(QTextCursor.End)

    def closeEvent(self, event):
        """
        Override. When Close Event Triggered.
        Ask user for saving modified files
        :param event:
        :return:
        """
        for i in range(len(self.openedEditors)):
            editor = self.openedEditors[i]
            editorTab = self.openedEditorTabs[i]
            if editor.document().isModified():
                name = ntpath.basename(editor.file) if editor.file else 'New File'
                ret = QMessageBox.warning(
                        self, name,
                        'The document has been modified.\nDo you want to save your changes?',
                        QMessageBox.Save | QMessageBox.Discard | QMessageBox.Cancel)
                if ret == QMessageBox.Save:
                    event.accept() if self.saveFile() else event.ignore()
                elif ret == QMessageBox.Discard:
                    index = self.ui.tabWidgetEditor.indexOf(editorTab)
                    self.ui.tabWidgetEditor.removeTab(index)
                    event.accept()
                else:
                    event.ignore()

    def showOutputPanel(self):
        """
        Clear previous output and show the ouput panel
        :return:
        """
        self.ui.console.clear()
        self.ui.tabWidgetOutput.show()

    def showBrowserTree(self, tab, rootNode):
        """
        Show treeView on tabWidgetBrowser
        :param tab:
        :param rootNode:
        """
        model = TreeModel(rootNode)

        if tab == self.ui.tabSyntax:
            treeView = self.ui.treeViewSyntax
            name = 'Syntax'
            self.ui.actionViewSystaxTree.setChecked(True)
        else:
            treeView = self.ui.treeViewToken
            name = 'Token'
            self.ui.actionViewTokenTree.setChecked(True)

        treeView.setModel(model)

        # show the tab
        index = self.ui.tabWidgetBrowser.indexOf(tab)
        if index == -1:
            self.ui.tabWidgetBrowser.addTab(tab, name)
            index = self.ui.tabWidgetBrowser.indexOf(tab)
        self.ui.tabWidgetBrowser.setCurrentIndex(index)

        self.addjustBrowserWidth()

    def connectMenuEditSlots(self):
        """
        set menu "Edit" signals connect to current editor slots
        :return:
        """
        self.ui.actionCopy.triggered.connect(self.currentEditor.copy)
        self.ui.actionCut.triggered.connect(self.currentEditor.cut)
        self.ui.actionPaste.triggered.connect(self.currentEditor.paste)
        self.ui.actionUndo.triggered.connect(self.currentEditor.undo)
        self.ui.actionRedo.triggered.connect(self.currentEditor.redo)
        self.ui.actionSelectAll.triggered.connect(self.currentEditor.selectAll)

    def disconnectMenuEditSlots(self):
        """
        disconnect menu "Edit" signals
        :return:
        """
        self.ui.actionCopy.triggered.disconnect(self.currentEditor.copy)
        self.ui.actionCut.triggered.disconnect(self.currentEditor.cut)
        self.ui.actionPaste.triggered.disconnect(self.currentEditor.paste)
        self.ui.actionUndo.triggered.disconnect(self.currentEditor.undo)
        self.ui.actionRedo.triggered.disconnect(self.currentEditor.redo)
        self.ui.actionSelectAll.triggered.disconnect(self.currentEditor.selectAll)

    def createEditorTab(self):
        """
        Create a new Editor tab and set as current editor
        Should reconnect the signal on menu 'Edit' actions
        :return:
        """
        # add a new editor
        self.currentEditorTab = QtWidgets.QWidget()
        horizontalLayout = QtWidgets.QHBoxLayout(self.currentEditorTab)
        horizontalLayout.setContentsMargins(0, 0, 0, 0)
        horizontalLayout.setSpacing(6)
        codeEditor = CodeEditor(self.currentEditorTab)
        horizontalLayout.addWidget(codeEditor)
        self.ui.tabWidgetEditor.addTab(self.currentEditorTab, "")

        # disconnect signals
        self.disconnectMenuEditSlots()

        # change current tab and editors
        self.currentEditor = codeEditor
        self.currentEditor.file = None
        self.openedEditors.append(self.currentEditor)
        self.openedEditorTabs.append(self.currentEditorTab)

        # connect signals
        self.connectMenuEditSlots()

        # set tab closeable
        if len(self.openedEditorTabs) > 1:
            self.ui.tabWidgetEditor.setTabsClosable(True)

    @pyqtSlot(int)
    def switchEditorTab(self, index):
        """
        Switch current active editor tab to index
        Should reconnect the signal on menu 'Edit' actions
        :param index:
        :return:
        """
        self.disconnectMenuEditSlots()
        self.currentEditorTab = self.openedEditorTabs[index]
        self.currentEditor = self.openedEditors[index]
        self.connectMenuEditSlots()

    @pyqtSlot(int)
    def closeEditorTab(self, index):
        """
        Triggered when closing the editor tab at index requested
        :param index:
        :return:
        """
        self.ui.tabWidgetEditor.removeTab(index)
        self.openedEditorTabs.pop(index)
        self.openedEditors.pop(index)
        self.switchEditorTab(0)  # choose the beginning tab as current active
        if len(self.openedEditorTabs) == 1:
            self.ui.tabWidgetEditor.setTabsClosable(False)

    @pyqtSlot(int)
    def closeBrowserTab(self, index):
        """
        Close Left Browser Tab at index
        :param index:
        :return:
        """
        # make menu "View" corresponding
        w = self.ui.tabWidgetBrowser.widget(index)
        if w == self.ui.tabFile:
            self.ui.actionViewFiles.setChecked(False)
        elif w == self.ui.tabToken:
            self.ui.actionViewTokenTree.setChecked(False)
        else:
            self.ui.actionViewSystaxTree.setChecked(False)

        # remove tab
        self.ui.tabWidgetBrowser.removeTab(index)
        if self.ui.tabWidgetBrowser.count() == 0:
            self.ui.tabWidgetBrowser.hide()

    @pyqtSlot(int)
    def closeOutputTab(self, index):
        """
        Close(hide) the output tab widget
        :param index:
        """

        # make menu "View" corresponding
        self.ui.actionViewConsole.setChecked(False)

        self.ui.tabWidgetOutput.hide()

    def recoverTabWidgets(self):
        """
        recover tabs when cancel maximizing
        :return:
        """
        for tab in self.preOpenedTabs:
            tab.show()
        self.preOpenedTabs = None

    def storeOpenedTabs(self):
        """
        store tabs opened before maximize
        :return:
        """
        self.preOpenedTabs = []
        if not self.ui.tabWidgetOutput.isHidden():
            self.preOpenedTabs.append(self.ui.tabWidgetOutput)
        if not self.ui.tabWidgetEditor.isHidden():
            self.preOpenedTabs.append(self.ui.tabWidgetEditor)
        if not self.ui.tabWidgetBrowser.isHidden():
            self.preOpenedTabs.append(self.ui.tabWidgetBrowser)

    def maximizeTabs(self, widget):
        if self.preOpenedTabs:
            self.recoverTabWidgets()
        else:
            self.storeOpenedTabs()
            for w in [self.ui.tabWidgetBrowser, self.ui.tabWidgetOutput, self.ui.tabWidgetEditor]:
                if w != widget:
                    w.hide()

    @pyqtSlot(QAction)
    def manageMenuView(self, action):
        """
        Handle the action on menu "View"
        :param action:
        :return:
        """
        if action == self.ui.actionViewToolbar:
            self.ui.toolBar.show() if action.isChecked() else self.ui.toolBar.hide()
            return

        pair = {
            self.ui.actionViewFiles: (self.ui.tabWidgetBrowser, self.ui.tabFile, 'File'),
            self.ui.actionViewTokenTree: (self.ui.tabWidgetBrowser, self.ui.tabToken, 'Token'),
            self.ui.actionViewSystaxTree: (self.ui.tabWidgetBrowser, self.ui.tabSyntax, 'Syntax'),
            self.ui.actionViewConsole: (self.ui.tabWidgetOutput, self.ui.tabConsole, 'Console'),
        }
        p = pair[action]
        widget = p[0]
        tab = p[1]
        name = p[2]

        if action.isChecked():
            widget.addTab(tab, name)
            widget.setCurrentWidget(tab)

            if widget == self.ui.tabWidgetBrowser:  # reset tab inner splitter size
                self.addjustBrowserWidth()

            if widget.isHidden():
                widget.show()
        else:
            widget.removeTab(
                    widget.indexOf(tab))
            if widget.count() == 0:
                widget.hide()

    def addjustBrowserWidth(self):
        w = self.ui.tabWidgetBrowser.count() * 80
        self.ui.splitterInner.setSizes([w, self.ui.splitterInner.width() - w])

    @pyqtSlot(bool)
    def openFile(self, checked=True, path=None):
        """
        Open a new file.
        If current editor is associated with a file or its content is not null,
        Then create a new editor tab
        :return:
        """
        path = QFileDialog.getOpenFileName()[0] if not path else path
        if len(path) != 0:
            qfile = QFile(path)
            if not qfile.open(QFile.ReadOnly or QFile.Text):
                QMessageBox.warning(self, 'Application',
                                    'Cannot read file %s:\n%s.' % (path, qfile.errorString()))
                return
            with open(path, 'r') as _file:
                content = _file.read()

            if self.currentEditor.file or len(self.currentEditor.document().toPlainText()) > 0:
                self.createEditorTab()

            # associate file on disk with editor
            self.currentEditor.file = path

            # update tab name
            index = self.ui.tabWidgetEditor.indexOf(self.currentEditorTab)
            _translate = QCoreApplication.translate
            self.ui.tabWidgetEditor.setTabText(
                    index, _translate("MainWindow", ntpath.basename(path)))
            self.ui.tabWidgetEditor.setCurrentIndex(index)
            self.currentEditor.setPlainText(content)

    @pyqtSlot(int)
    def openFileFromTree(self, index):
        f = self.fileTreeModel.fileInfo(index)
        if f.isFile():
            self.openFile(path=f.filePath())

    @pyqtSlot(bool)
    def newFile(self, checked):
        """
        create a new editor tab
        :param action:
        :return:
        """
        self.createEditorTab()
        index = self.ui.tabWidgetEditor.indexOf(self.currentEditorTab)
        _translate = QCoreApplication.translate
        self.ui.tabWidgetEditor.setTabText(
                index, _translate("MainWindow", 'New File'))
        self.ui.tabWidgetEditor.setCurrentIndex(index)

    @pyqtSlot(bool)
    def saveFile(self, checked=None):
        """
        Save file.
        If current editor is associated with a file on the disk,
        then save it. Or save file as...
        :param checked:
        :return: Saved or canceled
        """
        if self.currentEditor.file:
            if self.currentEditor.document().isModified():
                with open(self.currentEditor.file, 'w') as f:
                    f.write(self.currentEditor.document().toPlainText())
                self.currentEditor.document().setModified(False)
            return True
        else:
            return self.saveFileAs()

    @pyqtSlot(bool)
    def saveFileAs(self, checked=None):
        """
        Save File As...
        :param checked:
        :return: If saved or canceled
        """
        dialog = QFileDialog()
        dialog.setWindowModality(Qt.WindowModal)
        dialog.setAcceptMode(QFileDialog.AcceptSave)
        if dialog.exec_():
            filepath = dialog.selectedFiles()[0]
            with open(filepath, 'w') as f:
                f.write(self.currentEditor.document().toPlainText())
            self.currentEditor.document().setModified(False)
            self.currentEditor.file = filepath
            return True
        else:
            return False