Пример #1
0
    def showData(self, line):
        unicode_fonts = UnicodeFonts()

        for i, column in enumerate(line):
            text_edit = QGrowingTextEdit()

            unicode_fonts.applyFontAndSizeToQWidget(str(column), text_edit)

            text_edit.setText(str(column))
            text_edit.setObjectName("bla")
            text_edit.setReadOnly(True)
            self.layout.addWidget(text_edit)
Пример #2
0
    def editorTab(self, filepath):
        editor = QTextEdit()

        data = ""
        with open(filepath[0]) as fobj:
            for line in fobj:
                data += line

        unicode_fonts = UnicodeFonts()
        unicode_fonts.applyFontAndSizeToQWidget(data, editor)
        editor.setText(data)

        return editor
Пример #3
0
 def __init__(self):
     super().__init__()
     
     self.setWindowTitle("virtual keyboard")
     self.resize(450, 150)
     
     self.unicode_fonts = UnicodeFonts()
     
     #self.language = None
     self.keys = None
     self.level_one_chars = None
     self.level_two_chars = None
     
     self.modifier = Qt.NoModifier
     
     self.ipa_keyboard = IPAKeyboard()
Пример #4
0
    def __init__(self):
        super().__init__()

        self.unicode_fonts = UnicodeFonts()

        self.grid = QGridLayout()
        self.grid.setContentsMargins(0, 0, 0, 6)
        self.setLayout(self.grid)

        self.display_widget = QTextEditEnhanced()
        self.display_widget.setText(
            "type in the command 'man' down in the command line for getting started ..."
        )
        self.display_widget.setReadOnly(True)

        self.addDisplayWidget()

        line = QInputLine()
        line.setPlaceholderText(
            "This is the command line. See 'man commandline' for details.")
        line.return_pressed.connect(self.commandEntered)
        self.grid.addWidget(line, 1, 0)

        vkbdButton = QPushButton(self)
        vkbdButton.clicked.connect(partial(self.vkbdButtonClicked, line))
        vkbdButton.setIcon(QIcon.fromTheme('input-keyboard'))
        self.grid.addWidget(vkbdButton, 1, 1)

        zoomOutButton = QPushButton(self)
        zoomOutButton.setIcon(QIcon.fromTheme('zoom-out'))
        zoomOutButton.clicked.connect(self.onZoomOutClicked)
        self.grid.addWidget(zoomOutButton, 1, 2)

        zoomResetButton = QPushButton(self)
        zoomResetButton.setIcon(QIcon.fromTheme('zoom-original'))
        zoomResetButton.clicked.connect(self.onZoomResetClicked)
        self.grid.addWidget(zoomResetButton, 1, 3)

        zoomInButton = QPushButton(self)
        zoomInButton.setIcon(QIcon.fromTheme('zoom-in'))
        zoomInButton.clicked.connect(self.onZoomInClicked)
        self.grid.addWidget(zoomInButton, 1, 4)

        self.applyStylesheet()
Пример #5
0
 def __init__(self):
     super().__init__()
     
     self.unicode_fonts = UnicodeFonts()
Пример #6
0
class QDeckLearnWidget(QWidget):
    
    deckpath = None
    
    selectDeck = pyqtSignal()
    
    grid = None
    
    dataset = None
    number_of_data = None
    current_index = 0
    
    def __init__(self):
        super().__init__()
        
        self.unicode_fonts = UnicodeFonts()
        
    def initialize(self, deckpath):
        self.deckpath = deckpath
        
        try:
            self.clear()
        except SystemError:
            pass
        
        db_path = path.join(deckpath, "database.sqlite")
        self.dbAdapter = DeckDbAdapter()
        self.dbAdapter.initialize(db_path)
        
        deck_select_button = QPushButton("<<<")
        self.data_counter = QLabel()
        self.data_counter.setAlignment(Qt.AlignVCenter | Qt.AlignHCenter)
        
        deck_select_button.clicked.connect(self.selectDeckButtonClicked)
        
        
        self.current_name = QLabel()
        self.current_name.setAlignment(Qt.AlignVCenter | Qt.AlignHCenter)
        self.current_word = QLabel()
        self.current_word.setFont(QFont("Helvetica", 20))
        self.current_word.setAlignment(Qt.AlignVCenter | Qt.AlignHCenter)
        self.current_translation = QLabel()
        self.current_translation.setAlignment(Qt.AlignVCenter | Qt.AlignHCenter)
        
        button_prev = QPushButton('prev')
        button_next = QPushButton('next')
        button_show_translation = QPushButton('show translation')
        button_new_set = QPushButton('new set')
        button_known = QPushButton('known')
        button_not_known = QPushButton('not known')
        
        button_prev.clicked.connect(self.buttonPrevClicked)
        button_next.clicked.connect(self.buttonNextClicked)
        button_show_translation.clicked.connect(self.buttonShowTranslationClicked)
        button_new_set.clicked.connect(self.buttonNewSetClicked)
        button_known.clicked.connect(self.buttonKnownClicked)
        button_not_known.clicked.connect(self.buttonNotKnownClicked)
        
        self.svgWidget = QtSvg.QSvgWidget()
        self.svgWidget.setFixedSize(300, 150)
        self.svgWidget.setStyleSheet("background-color: rgb(255,0,0); margin:5px; border:1px solid rgb(0, 255, 0); ")
        
        self.buttonNewSetClicked()
        
        if not self.layout():
            self.grid = QGridLayout()
            self.grid.setContentsMargins(0, 0, 0, 0)
            self.grid.addWidget(deck_select_button, 0, 0)
            self.grid.addWidget(self.data_counter, 0, 2)
            #self.grid.addWidget(self.svgWidget, 1, 1)
            
            self.grid.addWidget(self.current_name, 4, 1)
            self.grid.addWidget(self.current_word, 5, 1)
            self.grid.addWidget(self.current_translation, 6, 1)
            
            self.grid.addWidget(button_prev, 7, 0)
            self.grid.addWidget(button_next, 8, 0)
            self.grid.addWidget(button_show_translation, 7, 1)
            self.grid.addWidget(button_new_set, 8, 1)
            self.grid.addWidget(button_known, 7, 2)
            self.grid.addWidget(button_not_known, 8, 2)
            
            layout = self.setLayout(self.grid)
    
    def clear(self):
        if self.grid:
            # just reparent the layout to a temporary one for delete it
            QWidget().setLayout(self.grid)
    
    def selectDeckButtonClicked(self):
        self.selectDeck.emit()
        
    def buttonPrevClicked(self):
        if self.current_index > 0:
            self.current_index -= 1
        else:
            self.current_index = len(self.dataset)-1
        
        self.setTexts()
        
    def buttonNextClicked(self):
        if self.current_index < len(self.dataset)-1:
            self.current_index += 1
        else:
            self.current_index = 0
        
        self.setTexts()
        
    def setTexts(self):
        try:
            self.current_word.setText(self.dataset[self.current_index]['word'])
        except IndexError:
            self.current_word.setText('ERROR: empty set')
        
        
        self.current_name.setText("")
        self.current_translation.setText("")
        
        self.svgWidget.load(path.join(self.deckpath, self.dataset[self.current_index]['svg_filename']))
        
        self.data_counter.setText(str(self.current_index+1) + "/" + str(self.number_of_data))
        
    def buttonShowTranslationClicked(self):
        try:
            self.current_name.setText(self.dataset[self.current_index]['name'])
            self.unicode_fonts.applyFontAndSizeToQWidget(self.dataset[self.current_index]['name'], self.current_name)
            
            self.current_translation.setText(self.dataset[self.current_index]['translation'])
            
            #self.current_translation.setFontPointSize(40)
            self.unicode_fonts.applyFontAndSizeToQWidget(self.dataset[self.current_index]['translation'], self.current_translation)
        except IndexError:
            self.current_name.setText('ERROR: empty set')
            self.current_translation.setText('ERROR: empty set')
        
    def buttonNewSetClicked(self):
        self.current_index = 0
        self.dataset = self.dbAdapter.getDataset()
        
        self.number_of_data = len(self.dataset)
        self.data_counter.setText(str(self.current_index+1) + "/" + str(self.number_of_data))
        self.current_name.setText("")#self.dataset[self.current_index]['name'])
        try:
            self.current_word.setText(self.dataset[self.current_index]['word'])
        except IndexError:
            self.current_word.setText("ERROR: empty set")
        self.current_translation.setText("")#self.dataset[self.current_index]['translation'])
        
        try:
            self.svgWidget.load(path.join(self.deckpath, self.dataset[self.current_index]['svg_filename']))
        except IndexError:
            """ we just do not have an svg-image """
            pass
    
    def buttonKnownClicked(self):
        self.dbAdapter.updateKnown(self.dataset[self.current_index]['rowid'], 1)
        self.buttonNextClicked()
        
    def buttonNotKnownClicked(self):
        self.dbAdapter.updateKnown(self.dataset[self.current_index]['rowid'], -1)
        self.buttonNextClicked()
Пример #7
0
class QCliWidget(QWidget):

    interpreter = Interpreter()
    display_widget = None
    vkbd = None
    beamer = None

    result_from_queue = False

    set_tab_text = pyqtSignal(str)

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

        self.unicode_fonts = UnicodeFonts()

        self.grid = QGridLayout()
        self.grid.setContentsMargins(0, 0, 0, 6)
        self.setLayout(self.grid)

        self.display_widget = QTextEditEnhanced()
        self.display_widget.setText(
            "type in the command 'man' down in the command line for getting started ..."
        )
        self.display_widget.setReadOnly(True)

        self.addDisplayWidget()

        line = QInputLine()
        line.setPlaceholderText(
            "This is the command line. See 'man commandline' for details.")
        line.return_pressed.connect(self.commandEntered)
        self.grid.addWidget(line, 1, 0)

        vkbdButton = QPushButton(self)
        vkbdButton.clicked.connect(partial(self.vkbdButtonClicked, line))
        vkbdButton.setIcon(QIcon.fromTheme('input-keyboard'))
        self.grid.addWidget(vkbdButton, 1, 1)

        zoomOutButton = QPushButton(self)
        zoomOutButton.setIcon(QIcon.fromTheme('zoom-out'))
        zoomOutButton.clicked.connect(self.onZoomOutClicked)
        self.grid.addWidget(zoomOutButton, 1, 2)

        zoomResetButton = QPushButton(self)
        zoomResetButton.setIcon(QIcon.fromTheme('zoom-original'))
        zoomResetButton.clicked.connect(self.onZoomResetClicked)
        self.grid.addWidget(zoomResetButton, 1, 3)

        zoomInButton = QPushButton(self)
        zoomInButton.setIcon(QIcon.fromTheme('zoom-in'))
        zoomInButton.clicked.connect(self.onZoomInClicked)
        self.grid.addWidget(zoomInButton, 1, 4)

        self.applyStylesheet()

    def applyStylesheet(self):
        config = ConfigFile(None, None)
        path = config.readVar('global', 'stylesheet')
        stylesheet = ''
        try:
            with open(path) as css:
                for line in css:
                    stylesheet += line

            self.display_widget.setStyleSheet(stylesheet)
        except FileNotFoundError:
            pass

    def addDisplayWidget(self):
        self.view = QGraphicsView()
        self.scene = QGraphicsScene()

        self.scene.addWidget(self.display_widget)
        self.view.setScene(self.scene)
        self.view.setStyleSheet("QGraphicsView { border-style: none; }")

        self.grid.addWidget(self.view, 0, 0, 1, 0)

        self.resizeDisplayWidget()

        self.applyStylesheet()

    def resizeDisplayWidget(self):
        # the magick numbers are for keeping the size of the view allways small enough not to spawn an outer set of scrollbars:
        x = self.view.width() - 2.1
        y = self.view.height() - 2.1
        self.x, self.y = x, y

        mapped_rect = self.view.mapToScene(QRect(0, 0, x, y)).boundingRect()

        self.display_widget.setFixedSize(mapped_rect.width(),
                                         mapped_rect.height())
        self.scene.setSceneRect(0, 0, mapped_rect.width(),
                                mapped_rect.height())

    def resizeEvent(self, event):
        self.resizeDisplayWidget()

    def vkbdButtonClicked(self, lineEdit):
        self.vkbd = QVirtualKeyboardWindow()
        self.vkbd.setLineEdit(lineEdit)

    def commandEntered(self, command):
        # to keep the display_widget in the correct size
        self.resize(self.x, self.y)

        print("command:", command)
        if '|' in command:
            command, pipe = command.split('|')
            self.handleCommand(command)

            pipe = pipe.strip()
            if pipe == 'beamer':
                if self.beamer:
                    self.beamer.destroy()
                    print('destroyed!!!')

                self.beamer = QBeamerWindow()

                from PyQt5.QtWidgets import QLabel, QPushButton
                widget = QLabel('blaaaa')

                self.beamer.setWidget(self.display_widget)
                #self.beamer.setText('test')
                self.beamer.routeToScreen()
                self.beamer.showFullScreen()
        else:
            #self.handleCommand(command)
            self.set_tab_text.emit(command)

            #self.activityIndicator()

            q = queue.Queue()

            self.interpreter_thread = HandleCommandThread(command, q)
            self.interpreter_thread.processResult.connect(self.processResult)
            self.interpreter_thread.clearDisplayWidget.connect(
                self.clearDisplayWidget)
            self.interpreter_thread.makeSnapshot.connect(self.makeSnapshot)
            self.interpreter_thread.stopQueueListener.connect(
                self.stopQueueListener)
            self.interpreter_thread.start()

            self.queue_thread = GetQueueItemsThread(q)
            self.queue_thread.processQueueItem.connect(self.processQueueItem)
            self.queue_thread.start()

    def stopQueueListener(self):
        self.queue_thread.stop()

    def processQueueItem(self, item):
        self.result_from_queue = True

        item = item.getItem()

        json_dict = json.loads(item)
        if json_dict['category'] == 'progressbar':
            last_type = type(self.display_widget)
            if not last_type == QProgressBar:
                self.display_widget.deleteLater()
                self.display_widget = QProgressBar()

            self.display_widget.setMinimum(json_dict['minimum'])
            self.display_widget.setMaximum(json_dict['maximum'])
            self.display_widget.setValue(json_dict['value'])

            if not last_type == QProgressBar:
                self.addDisplayWidget()

        else:
            result_object = Result()
            result_object.payload = item.getItem()
            self.resultInTextEdit(result_object)

    def processResult(self, result):
        if self.result_from_queue:
            self.result_from_queue = False

        else:
            #if result is None:
            #self.showErrorMessage('no result found')

            if hasattr(result, 'payload') and result.payload:
                if hasattr(result, 'category') and result.category == "table":
                    try:
                        result.payload[0]
                    except IndexError:
                        pass  # datastructure does not fit to display type 'table'
                    else:
                        self.resultInTable(result)

                elif hasattr(
                        result,
                        'category') and result.category == "multimedia_table":
                    self.resultInMultimediaTable(result)

                elif hasattr(result, 'category') and result.category == "list":
                    self.resultInTextEdit(result)

                elif hasattr(result, 'category') and result.category == "text":
                    self.resultInTextEdit(result)

                elif hasattr(result,
                             'category') and result.category == "string":
                    self.resultInTextEdit(result)

                elif hasattr(result,
                             'category') and result.category == "itemized":
                    self.resultInItemizedWidget(result)

                elif hasattr(result,
                             'category') and result.category == "image":
                    self.resultInImageWidget(result)

                elif hasattr(result, 'category') and result.category == "html":
                    #self.resultInHTMLWidget(result)
                    self.resultInTextEdit(result)

                elif hasattr(result,
                             'category') and result.category == 'diagram':
                    self.resultInDiagram(result)

                elif hasattr(result,
                             'category') and result.category == 'bloodline':
                    self.resultInBloodlineDiagram(result)

                elif hasattr(result,
                             'category') and result.category == 'command':
                    self.showMapWidget()

            elif hasattr(result, 'error') and result.error:
                self.showErrorMessage(result.error)

            else:
                result = Result()
                result.payload = 'empty result set'
                self.resultInTextEdit(result)

    def activityIndicator(self):
        self.display_widget.deleteLater()

        label = QLabel()
        movie = QMovie('./assets/images/activity_indicator.gif')
        movie.start()
        label.setMovie(movie)

        self.display_widget = QWidget()
        layout = QVBoxLayout()
        self.display_widget.setLayout(layout)
        layout.addWidget(label, Qt.AlignCenter)

        self.addDisplayWidget()

    def clearDisplayWidget(self):
        self.display_widget.deleteLater()
        self.display_widget = QTextEditEnhanced()
        self.display_widget.setReadOnly(True)
        self.addDisplayWidget()

    def makeSnapshot(self):
        image = QImage(self.display_widget.size(), QImage.Format_ARGB32)
        painter = QPainter(image)

        if painter.isActive():
            self.render(painter)

        painter.end()

        default_dir = path.join(path.expanduser('~'))
        filename = QFileDialog.getSaveFileName(self, 'Save Snapshot',
                                               default_dir)

        image.save(filename[0])

    def resultInTable(self, result):
        self.display_widget.deleteLater()
        self.display_widget = QTableWidget()
        self.display_widget.setRowCount(len(result.payload))
        self.display_widget.setColumnCount(len(result.payload[0]))

        try:
            self.display_widget.setHorizontalHeaderLabels(result.header)
        except TypeError:
            pass
        try:
            self.display_widget.setVerticalHeaderLabels(result.header_left)
        except TypeError:
            pass

        for row, line in enumerate(result.payload):
            for column, item in enumerate(line):
                table_item = QTableWidgetItem(str(item))
                table_item.setFlags(Qt.ItemIsEnabled)
                self.unicode_fonts.applyFontToQWidget(str(item), table_item)
                self.display_widget.setItem(row, column, table_item)

        self.display_widget.resizeColumnsToContents()
        self.addDisplayWidget()

    def resultInMultimediaTable(self, result):
        self.display_widget.deleteLater()

        max_length = 0
        for line in result.payload:
            if len(line) > max_length:
                max_length = len(line)

        self.display_widget = QTableWidget()
        self.display_widget.setRowCount(len(result.payload))
        self.display_widget.setColumnCount(max_length)

        audio_count = 0
        config = ConfigFile(None, None)
        deckpath = config.readPath("vocable", "deckpath")
        for row, line in enumerate(result.payload):
            deckname = line[0]
            for column, item in enumerate(line):
                if self.isImage(str(item)):
                    pixmap = QPixmap()
                    pixmap.load(path.join(deckpath, deckname, str(item)))
                    pixmap = pixmap.scaled(QSize(60, 30), Qt.KeepAspectRatio)
                    image_widget = QLabel()
                    image_widget.setPixmap(pixmap)
                    self.display_widget.setCellWidget(row, column,
                                                      image_widget)
                elif self.isAudio(str(item)):
                    splitted = item.split(',')
                    if audio_count < len(splitted):
                        audio_count = len(splitted)
                    audio_widget = QAudioItems(path.join(deckpath, deckname),
                                               self.display_widget, 7,
                                               max_length)
                    audio_widget.appendPlayButtonsList(splitted, row)
                else:
                    table_item = QTableWidgetItem(str(item))
                    table_item.setFlags(Qt.ItemIsEnabled)
                    #self.unicode_fonts.applyFontToQWidget(str(item), table_item)
                    self.display_widget.setItem(row, column, table_item)

        self.display_widget.setColumnCount(max_length + audio_count)
        self.display_widget.resizeColumnsToContents()
        self.addDisplayWidget()

    def resultInTextEdit(self, result):
        self.display_widget.deleteLater()
        self.display_widget = QTextEditEnhanced()

        self.unicode_fonts.applyFontAndSizeToQWidget(result.toString(),
                                                     self.display_widget)

        self.display_widget.setAcceptRichText(True)

        self.display_widget.setText(result.toString())
        self.display_widget.setReadOnly(True)
        self.display_widget.setTextInteractionFlags(
            self.display_widget.textInteractionFlags()
            | Qt.TextSelectableByKeyboard)
        self.addDisplayWidget()

    def resultInHTMLWidget(self, result):
        self.display_widget.deleteLater()
        self.display_widget = QWebView()

        self.display_widget.setHtml(result.payload)
        self.addDisplayWidget()

    def resultInItemizedWidget(self, result):
        self.display_widget.deleteLater()
        self.display_widget = QItemizedWidget(result.payload)
        self.addDisplayWidget()

    def resultInImageWidget(self, result):
        self.display_widget.deleteLater()

        self.display_widget = QCustomizedGraphicsView()

        import PIL
        if type(result.payload) == PIL.Image.Image:
            from PIL.ImageQt import ImageQt
            qimage = ImageQt(result.payload)
            pixmap = QPixmap.fromImage(qimage)

        #pixmap = QPixmap("/tmp/tmprp3q0gi9.PNG")
        #pixmap.fromImage(image)

        item = self.display_widget.scene().addPixmap(pixmap)
        item.setPos(0, 0)
        self.addDisplayWidget()

    def resultInDiagram(self, result):
        self.display_widget.deleteLater()

        curve = QLineSeries()
        pen = curve.pen()
        pen.setColor(Qt.red)
        pen.setWidthF(2)
        curve.setPen(pen)

        for data in result.payload:
            if type(data['y']) == str:
                data['y'] = 0
            curve.append(data['x'], data['y'], 10)

        chart = QChart()
        chart.setTitle(result.name)
        chart.legend().hide()
        chart.addSeries(curve)
        chart.createDefaultAxes()

        view = QChartViewEnhanced(chart)
        view.setRenderHint(QPainter.Antialiasing)
        self.display_widget = view
        self.addDisplayWidget()

    def resultInBloodlineDiagram(self, result):
        self.display_widget.deleteLater()
        self.display_widget = QBloodlineWidget(result.payload)
        self.addDisplayWidget()

    def showMapWidget(self):
        self.display_widget.deleteLater()

        self.display_widget = QMapWidget()
        self.display_widget.showPosition()

        self.addDisplayWidget()

    def showErrorMessage(self, message):
        self.display_widget.deleteLater()
        self.display_widget = QTextEditEnhanced()
        self.display_widget.setText(message)
        self.display_widget.setReadOnly(True)
        self.addDisplayWidget()

    def onZoomInClicked(self):
        if type(self.display_widget) == QTextEditEnhanced:
            self.display_widget.zoomIn()
        elif type(self.display_widget) == QChartViewEnhanced:
            self.display_widget.chart().zoomIn()
        else:
            self.view.scale(SCALE_FACTOR, SCALE_FACTOR)
            self.resizeDisplayWidget()

    def onZoomOutClicked(self):
        if type(self.display_widget) == QTextEditEnhanced:
            self.display_widget.zoomOut()
        elif type(self.display_widget) == QChartViewEnhanced:
            self.display_widget.chart().zoomOut()
        else:
            self.view.scale(1 / SCALE_FACTOR, 1 / SCALE_FACTOR)
            self.resizeDisplayWidget()

    def onZoomResetClicked(self):
        if type(self.display_widget) == QTextEditEnhanced:
            self.display_widget.zoomReset()
        elif type(self.display_widget) == QChartViewEnhanced:
            self.display_widget.chart().zoomReset()
        else:
            self.view.resetTransform()
            self.resizeDisplayWidget()

    def keyPressEvent(self, event):
        if (event.modifiers() & Qt.ControlModifier):
            if event.key() == Qt.Key_Plus:
                self.onZoomInClicked()

            elif event.key() == Qt.Key_Minus:
                self.onZoomOutClicked()

    def isImage(self, data):
        suffixes = ['.png', '.jpg', '.jpe', '.jpeg', '.svg', '.bmp']
        for suffix in suffixes:
            if data.lower().endswith(suffix):
                return True
        return False

    def isAudio(self, data):
        suffixes = ['.ogg', '.wav', '.mp3', '.aiff', '.wma']
        for suffix in suffixes:
            if data.lower().endswith(suffix):
                return True
        return False
Пример #8
0
class QDeckOverviewWidget(QWidget):

    deckpath = None

    selectDeck = pyqtSignal()
    createNewItem = pyqtSignal(str, object, str)
    editDeckItem = pyqtSignal(str, object, int, str)

    tableWidget = None
    audioWidget = None

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

        self.unicodeFonts = UnicodeFonts()

    def initialize(self, deckpath, deckname):
        self.deckpath = deckpath
        self.deckname = deckname

        db_path = path.join(deckpath, "database.sqlite")
        self.dbAdapter = DeckDbAdapter()
        self.dbAdapter.initialize(db_path)

        deck_select_button = QPushButton("<<<")
        deck_select_button.clicked.connect(self.selectDeckButtonClicked)

        new_item_button = QPushButton("new item")
        new_item_button.clicked.connect(self.newItemButtonClicked)

        stop_all_sounds_button = QPushButton("stop all sounds")
        stop_all_sounds_button.clicked.connect(self.stopAllSounds)

        self.initTableWidget()

        if not self.layout():
            self.grid = QGridLayout()
            self.grid.setContentsMargins(0, 0, 0, 0)
            self.grid.addWidget(deck_select_button, 0, 0)
            self.grid.addWidget(self.tableWidget, 1, 0, 1, 3)
            self.grid.addWidget(new_item_button, 2, 0)
            self.grid.addWidget(stop_all_sounds_button, 2, 2)

            layout = self.setLayout(self.grid)

        self.initWithDbData()

    def initTableWidget(self):
        if not self.tableWidget:
            self.tableWidget = QTableWidget()

        self.tableWidget.setColumnCount(8)
        self.tableWidget.setRowCount(0)
        self.tableWidget.setHorizontalHeaderLabels(
            ["", "", "id", "name", "word", "translation", "svg", "audio"])
        self.tableWidget.verticalHeader().hide()
        self.tableWidget.horizontalHeader().hide()

    def initWithDbData(self):
        self.tableWidget.clear()

        data = self.dbAdapter.selectDeckItems()
        #data = self.dbAdapter.selectDeckItemsWithAudio()
        self.tableWidget.setRowCount(len(data))

        max_audio_count = self.dbAdapter.getMaxAudioCount()
        self.audioWidget = QAudioItems(self.deckpath, self.tableWidget,
                                       max_audio_count, COLUMN_OFFSET)

        for i, line in enumerate(data):
            rowid = line["rowid"]
            order_index = line["order_index"]
            name = line["name"]
            word = line["word"]
            phonetical = line["phonetical"]
            translation = line["translation"]
            svg_filename = line["svg_filename"]
            image_filename = None
            imageWidget = QLabel()
            try:
                image_filename = line["image"]
            except:
                """ maybe we have an image, maybe not ... """
                pass
            else:
                pixmap = QPixmap()
                try:
                    pixmap.load(path.join(self.deckpath, image_filename))
                except TypeError:
                    """ probably we have an None-image here """
                    pass
                else:
                    pixmap = pixmap.scaled(QSize(60, 30), Qt.KeepAspectRatio)
                    imageWidget.setPixmap(pixmap)

            audio_filenames = self.dbAdapter.audioFilenamesForDeckRowID(rowid)

            try:
                svgWidget = QtSvg.QSvgWidget(
                    path.join(self.deckpath, svg_filename))
            except TypeError:
                svgWidget = QtSvg.QSvgWidget()
            #svgWidget.setGeometry(50,50,759,668)
            svgWidget.setFixedSize(60, 30)

            edit_button = QPushButton()  #"edit")
            edit_button.setIcon(QIcon.fromTheme("document-properties"))
            edit_button.clicked.connect(
                partial(self.editRowButtonClicked, rowid))
            delete_button = QPushButton()  #"delete")
            delete_button.setIcon(QIcon.fromTheme('edit-delete'))
            delete_button.clicked.connect(
                partial(self.deleteRowButtonClicked, rowid))

            self.tableWidget.setCellWidget(i, 0, edit_button)
            self.tableWidget.setCellWidget(i, 1, delete_button)
            self.tableWidget.setItem(i, 2, QTableWidgetItem(str(order_index)))
            self.tableWidget.setItem(i, 3, QTableWidgetItem(name))
            self.tableWidget.setItem(i, 4, QTableWidgetItem(word))

            phonetical_item = QTableWidgetItem(phonetical)
            self.unicodeFonts.setFont('ipa', phonetical_item)
            self.tableWidget.setItem(i, 5, phonetical_item)

            self.tableWidget.setItem(i, 6, QTableWidgetItem(translation))
            self.tableWidget.setCellWidget(i, 7, svgWidget)
            self.tableWidget.setCellWidget(i, 8, imageWidget)

            #if audio_filenames:
            print("AUDIO_FILENAMES")
            print(audio_filenames)
            self.audioWidget.appendPlayButtonsDict(audio_filenames, i)

        #column_count = self.audioWidget.getMaxColCount()
        #self.tableWidget.setColumnCount(column_count)
        self.tableWidget.setColumnCount(COLUMN_OFFSET + max_audio_count)
        self.tableWidget.resizeColumnsToContents()

    def selectDeckButtonClicked(self):
        self.selectDeck.emit()

    def newItemButtonClicked(self):
        self.createNewItem.emit(self.deckpath, self.dbAdapter, self.deckname)

    def editRowButtonClicked(self, rowid):
        self.editDeckItem.emit(self.deckpath, self.dbAdapter, int(rowid),
                               self.deckname)

    def deleteRowButtonClicked(self, rowid):

        delete_msg = "really?"
        reply = QMessageBox.question(self, 'Delete', delete_msg,
                                     QMessageBox.Yes, QMessageBox.No)

        if reply == QMessageBox.Yes:
            svg_filename, audio_filenames = self.dbAdapter.deleteItem(rowid)
            if svg_filename:
                remove(path.join(self.deckpath, svg_filename))
                pass

            for audio in audio_filenames:
                if path.exists(path.join(self.deckpath, audio)):
                    remove(path.join(self.deckpath, audio))

            self.initWithDbData()

    def stopAllSounds(self):
        self.audioWidget.stopAllSounds()
Пример #9
0
    def __init__(self):
        super().__init__()

        self.unicode_fonts = UnicodeFonts()
        self.default_bible = self.config.readVar('global', 'default_bible')

        self.grid = QGridLayout()
        self.grid.setContentsMargins(0, 0, 0, 6)
        self.setLayout(self.grid)

        self.text_edit = QTextEditEnhanced()

        self.combo_language = QComboBox()
        self.combo_translation = QComboBox()
        self.combo_book = QComboBox()
        self.combo_chapter = QComboBox()

        self.combo_language.currentTextChanged.connect(self.languageChanged)
        self.combo_translation.currentTextChanged.connect(
            self.translationChanged)
        self.combo_book.currentTextChanged.connect(self.bookChanged)

        self.prev_verse_button = QPushButton("<")
        self.prev_verse_button.setMaximumSize(25, 25)
        self.next_verse_button = QPushButton(">")
        self.next_verse_button.setMaximumSize(25, 25)

        self.prev_verse_button.clicked.connect(self.prevChapter)
        self.next_verse_button.clicked.connect(self.nextChapter)

        self.grid.addWidget(QLabel("Language"), 0, 0)
        self.grid.addWidget(QLabel("Translation"), 0, 1)
        self.grid.addWidget(QLabel("Book"), 0, 2)
        self.grid.addWidget(QLabel("Chapter"), 0, 3)

        self.grid.addWidget(self.combo_language, 1, 0)
        self.grid.addWidget(self.combo_translation, 1, 1)
        self.grid.addWidget(self.combo_book, 1, 2)
        self.grid.addWidget(self.combo_chapter, 1, 3)
        self.grid.addWidget(self.prev_verse_button, 1, 4)
        self.grid.addWidget(self.next_verse_button, 1, 5)

        zoom_in_button = QPushButton(self)
        zoom_in_button.setIcon(QIcon.fromTheme('zoom-in'))
        zoom_in_button.clicked.connect(self.onZoomInClicked)
        zoom_in_button.setMaximumSize(25, 25)

        zoom_out_button = QPushButton(self)
        zoom_out_button.setIcon(QIcon.fromTheme('zoom-out'))
        zoom_out_button.clicked.connect(self.onZoomOutClicked)
        zoom_out_button.setMaximumSize(25, 25)

        zoom_reset_button = QPushButton(self)
        zoom_reset_button.setIcon(QIcon.fromTheme('zoom-original'))
        zoom_reset_button.clicked.connect(self.onZoomResetClicked)
        zoom_reset_button.setMaximumSize(25, 25)

        self.grid.addWidget(zoom_out_button, 1, 6)
        self.grid.addWidget(zoom_reset_button, 1, 7)
        self.grid.addWidget(zoom_in_button, 1, 8)

        self.grid.addWidget(self.text_edit, 2, 0, 1000, 9)

        self.getLanguagesForDropdown()
        self.getBooksForDropdown()

        self.setDefaultBible()
        self.restoreLastBookAndChapter()
        """ this has to be after setting the default values to avoid spamming the history on init and to avoid to much gui-updates on init """
        self.combo_chapter.currentTextChanged.connect(self.chapterChanged)
Пример #10
0
class QSwordGui(QWidget):

    interpreter = Interpreter()
    queue = queue.Queue()

    sword = Sword()

    config = ConfigFile(os.path.join('modules', 'sword'), 'sword.conf')
    history = History("history_sword")

    set_tab_text = pyqtSignal(str)

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

        self.unicode_fonts = UnicodeFonts()
        self.default_bible = self.config.readVar('global', 'default_bible')

        self.grid = QGridLayout()
        self.grid.setContentsMargins(0, 0, 0, 6)
        self.setLayout(self.grid)

        self.text_edit = QTextEditEnhanced()

        self.combo_language = QComboBox()
        self.combo_translation = QComboBox()
        self.combo_book = QComboBox()
        self.combo_chapter = QComboBox()

        self.combo_language.currentTextChanged.connect(self.languageChanged)
        self.combo_translation.currentTextChanged.connect(
            self.translationChanged)
        self.combo_book.currentTextChanged.connect(self.bookChanged)

        self.prev_verse_button = QPushButton("<")
        self.prev_verse_button.setMaximumSize(25, 25)
        self.next_verse_button = QPushButton(">")
        self.next_verse_button.setMaximumSize(25, 25)

        self.prev_verse_button.clicked.connect(self.prevChapter)
        self.next_verse_button.clicked.connect(self.nextChapter)

        self.grid.addWidget(QLabel("Language"), 0, 0)
        self.grid.addWidget(QLabel("Translation"), 0, 1)
        self.grid.addWidget(QLabel("Book"), 0, 2)
        self.grid.addWidget(QLabel("Chapter"), 0, 3)

        self.grid.addWidget(self.combo_language, 1, 0)
        self.grid.addWidget(self.combo_translation, 1, 1)
        self.grid.addWidget(self.combo_book, 1, 2)
        self.grid.addWidget(self.combo_chapter, 1, 3)
        self.grid.addWidget(self.prev_verse_button, 1, 4)
        self.grid.addWidget(self.next_verse_button, 1, 5)

        zoom_in_button = QPushButton(self)
        zoom_in_button.setIcon(QIcon.fromTheme('zoom-in'))
        zoom_in_button.clicked.connect(self.onZoomInClicked)
        zoom_in_button.setMaximumSize(25, 25)

        zoom_out_button = QPushButton(self)
        zoom_out_button.setIcon(QIcon.fromTheme('zoom-out'))
        zoom_out_button.clicked.connect(self.onZoomOutClicked)
        zoom_out_button.setMaximumSize(25, 25)

        zoom_reset_button = QPushButton(self)
        zoom_reset_button.setIcon(QIcon.fromTheme('zoom-original'))
        zoom_reset_button.clicked.connect(self.onZoomResetClicked)
        zoom_reset_button.setMaximumSize(25, 25)

        self.grid.addWidget(zoom_out_button, 1, 6)
        self.grid.addWidget(zoom_reset_button, 1, 7)
        self.grid.addWidget(zoom_in_button, 1, 8)

        self.grid.addWidget(self.text_edit, 2, 0, 1000, 9)

        self.getLanguagesForDropdown()
        self.getBooksForDropdown()

        self.setDefaultBible()
        self.restoreLastBookAndChapter()
        """ this has to be after setting the default values to avoid spamming the history on init and to avoid to much gui-updates on init """
        self.combo_chapter.currentTextChanged.connect(self.chapterChanged)

    def languageChanged(self, language):
        self.getTranslationsForDropdown(language)

    def translationChanged(self, translation):
        self.showText()

    def bookChanged(self, book):
        self.getChaptersForDropdown(book)

    def chapterChanged(self, chapter):
        self.showText()

    def prevChapter(self):
        chapter = self.combo_chapter.currentText()
        self.combo_chapter.setCurrentText(str(int(chapter) - 1))

        self.showText()

    def nextChapter(self):
        chapter = self.combo_chapter.currentText()
        self.combo_chapter.setCurrentText(str(int(chapter) + 1))

        self.showText()

    def getLanguagesForDropdown(self):
        #result = self.interpreter.interpreter('sword.languages', self.queue).payload
        result = self.sword.listLanguages(None, []).payload
        if result is None:
            self.text_edit.clear()
            self.text_edit.setText(
                "no sword modules (=bibles) installed. please install some using the \"Sword->Module Manager\" menu entry."
            )
        else:
            self.combo_language.clear()
            self.combo_language.insertItems(0, result)

    def getTranslationsForDropdown(self, language):
        #result = self.interpreter.interpreter('sword.modules '+language, self.queue).payload
        result = self.sword.listModules(None, [language]).payload

        translations = []
        for translation in result:
            translations.append(translation[0])

        self.combo_translation.clear()
        self.combo_translation.insertItems(0, translations)

    def setDefaultBible(self):
        #sword_modules = self.interpreter.interpreter('sword.modules', self.queue).payload
        sword_modules = self.sword.listModules(None, []).payload

        for module in sword_modules:
            if module[0] == self.default_bible:
                self.combo_language.setCurrentText(module[1])
                self.combo_translation.setCurrentText(self.default_bible)

    def restoreLastBookAndChapter(self):
        last = self.history.historyReadAtIndex(3)
        try:
            translation, book, chapter = last.split(" ")

            self.combo_book.setCurrentText(book)
            self.combo_chapter.setCurrentText(chapter)

            self.showText()
        except ValueError:
            # probably we have an empty history-file
            pass

    def getBooksForDropdown(self):
        #books = self.interpreter.interpreter('sword.books', self.queue).payload
        books = self.sword.books(None, []).payload

        self.combo_book.clear()
        self.combo_book.insertItems(0, books)

    def getChaptersForDropdown(self, book):
        books = self.sword.canons()

        for testament in books:
            for _b in books[testament]:
                if _b[0] == book:
                    chapters = []
                    for i, length in enumerate(_b[3]):
                        chapters.append(str(i + 1))

                    self.combo_chapter.clear()
                    self.combo_chapter.insertItems(0, chapters)
                    break

            # if the inner 'break' was executed, we also want to break the outer loop:
            else:
                continue  # executed if the loop ended normally (no break)
            break  # executed if 'continue' was skipped (break)

    def showText(self):
        current_translation = self.interpreter.interpreter(
            'sword.getModule', self.queue).payload

        translation = self.combo_translation.currentText()
        book = self.combo_book.currentText()
        chapter = self.combo_chapter.currentText()

        if translation:
            self.interpreter.interpreter('sword.setModule ' + translation,
                                         self.queue)
            text = self.interpreter.interpreter(
                'sword.word "' + book + '" ' + chapter, self.queue)
            text = text.toString()
            self.interpreter.interpreter(
                'sword.setModule ' + current_translation, self.queue)

            self.text_edit.clear()
            self.text_edit.setText(text)
            self.text_edit.append("\nEND")
            self.text_edit.setReadOnly(True)

            self.text_edit.setTextInteractionFlags(
                self.text_edit.textInteractionFlags()
                | Qt.TextSelectableByKeyboard)

            self.unicode_fonts.applyFontAndSizeToQWidget(text, self.text_edit)

            if book and chapter:
                self.set_tab_text.emit(translation + ": " + book + " " +
                                       chapter)
                self.history.historyWrite(translation + ": " + book + " " +
                                          chapter)

    def onZoomInClicked(self):
        self.text_edit.zoomIn()

    def onZoomOutClicked(self):
        self.text_edit.zoomOut()

    def onZoomResetClicked(self):
        self.text_edit.zoomReset()
Пример #11
0
class QDeckDirtyDozenWidget(QWidget):

    deckpath = None

    grid = None

    selectDeck = pyqtSignal()

    dataset = None
    #audio_data = None
    audioPlayer = None

    curent_audio_deck_id = None

    last_random_audio = None
    """ holds one of DISPLAY_COMBO_ITEMS: """
    test_mode = 'image'

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

        self.unicode_fonts = UnicodeFonts()

    def initialize(self, deckpath):
        self.deckpath = deckpath

        #self.clear()

        self.audioPlayer = QMediaPlayer()

        db_path = path.join(deckpath, "database.sqlite")
        self.dbAdapter = DeckDbAdapter()
        self.dbAdapter.initialize(db_path)
        self.full_dataset = self.dbAdapter.selectDeckDirtyDozenItems()

        self.counter = 1
        self.delay_counter = 0
        self.delay = 2

        self.update()

    def update(self):
        self.clear()

        self.dataset = self.full_dataset[0:self.counter]

        deck_select_button = QPushButton("<<<")
        deck_select_button.clicked.connect(self.selectDeckButtonClicked)

        self.show_all_button = QPushButton("show all")
        self.show_all_button.clicked.connect(self.showAllButtonClicked)
        self.show_all_button_state = "show_all"

        replay_audio_button = QPushButton("replay audio")
        replay_audio_button.setIcon(QIcon.fromTheme('media-playback-start'))
        replay_audio_button.clicked.connect(self.replayAudioClicked)

        select_display_combo_label = QLabel('select display:')
        select_display_combo_label.setAlignment(QtCore.Qt.AlignRight)
        select_display_combo = QComboBox()
        select_display_combo.addItems(DISPLAY_COMBO_ITEMS)
        select_display_combo.setCurrentIndex(
            DISPLAY_COMBO_ITEMS.index(self.test_mode))
        select_display_combo.currentIndexChanged.connect(
            self.selectDisplayCurrentIndexChanged)

        instruction_label = QLabel(
            "[please click the image which you think is assigned to the spoken word!]"
        )

        if not self.layout():
            self.grid = QGridLayout()
            self.grid.setContentsMargins(0, 0, 0, 0)

        self.grid.addWidget(deck_select_button, 0, 0)
        self.grid.addWidget(select_display_combo_label, 0, 1)
        self.grid.addWidget(select_display_combo, 0, 2)
        self.grid.addWidget(replay_audio_button, 0, 3)

        for i, value in enumerate(self.dataset, COLUMNS):
            label = QClickLabel()
            if self.test_mode == 'image':
                preview_pixmap = QPixmap()
                try:
                    preview_pixmap.load(
                        path.join(self.deckpath, value["image"]))
                except (KeyError, TypeError):
                    try:
                        preview_pixmap.load(
                            path.join(self.deckpath, value["svg_filename"]))
                    except (KeyError, TypeError):
                        pass
                scaled_pixmap = preview_pixmap.scaled(
                    QtCore.QSize(200, 200), QtCore.Qt.KeepAspectRatio)
                label.setGeometry(scaled_pixmap.rect())
                label.setPixmap(scaled_pixmap)
            elif self.test_mode == 'name':
                label.setText(value['name'])
            elif self.test_mode == 'word':
                label.setText(value['word'])
            elif self.test_mode == 'translation':
                label.setText(value['translation'])

            self.unicode_fonts.applyFontAndSizeToQWidget(label.text(), label)

            label.setAlignment(QtCore.Qt.AlignCenter)
            label.clicked.connect(
                functools.partial(self.labelClicked, value["rowid"]))

            self.grid.addWidget(label, int(i / COLUMNS), i % COLUMNS)

        self.grid.addWidget(self.show_all_button, len(self.dataset) + 1, 0)
        self.grid.addWidget(instruction_label, len(self.dataset) + 1, 1, 1, 3)

        self.setLayout(self.grid)

        self.playRandomAudio()

    def clear(self):
        if self.grid:
            for i in range(0, self.layout().count()):
                widget = self.layout().itemAt(i).widget()
                widget.setVisible(False)

    def selectDeckButtonClicked(self):
        self.selectDeck.emit()

    def showAllButtonClicked(self):
        if self.show_all_button_state == "show_all":
            self.counter = len(self.full_dataset)
            self.update()

            self.show_all_button.setText("start over")
            self.show_all_button_state = "start_over"
        else:
            self.counter = 1
            self.delay_counter = 0
            self.delay = 2

            self.update()

    def labelClicked(self, row_id):
        try:
            if row_id == self.current_audio_deck_id:
                self.delay_counter += 1

                if len(self.full_dataset) > self.counter:
                    if self.delay_counter >= self.delay:
                        if self.delay_counter == 1:
                            self.delay = 5

                        elif self.delay_counter == 2:
                            self.delay = 5

                        else:
                            self.delay = 10

                        self.delay_counter = 0

                        self.counter += 1
                        self.update()

                        self.playNextAudio()

                    else:
                        self.playRandomAudio()
                else:
                    self.playRandomAudio()

        except AttributeError:
            """ we probably have no audio file in this module """
            pass

    def playNextAudio(self):
        self.playAudio(len(self.dataset) - 1)

    def playRandomAudio(self):
        try:
            selector = randint(0, len(self.dataset) - 1)

            if self.counter > 1:
                """ we do not want the same audio played multiple times on a row """
                depth = 0
                while selector == self.last_random_audio:
                    selector = randint(0, len(self.dataset) - 1)
                    """ to avoid infinite loops with just one element """
                    depth += 1
                    if depth > 20:
                        break

            self.last_random_audio = selector

            self.playAudio(selector)

        except ValueError:
            """ probably an empty deck. just do nothing"""
            pass

    def playAudio(self, selector):
        filename = self.dataset[selector]["filename"]
        self.current_audio_deck_id = self.dataset[selector]["rowid"]

        filepath = path.join(self.deckpath, filename)
        url = QtCore.QUrl.fromLocalFile(
            QtCore.QFileInfo(filepath).absoluteFilePath())
        content = QMediaContent(url)
        self.audioPlayer.setMedia(content)
        self.audioPlayer.play()

    def replayAudioClicked(self):
        self.audioPlayer.play()

    def selectDisplayCurrentIndexChanged(self, test):
        selected_label = DISPLAY_COMBO_ITEMS[test]
        self.clear()
        self.test_mode = selected_label

        self.initialize(self.deckpath)
Пример #12
0
class QVirtualKeyboardWidget(QWidget):
    
    keyPressedAny = pyqtSignal(int)
    lineEdit = None
    
    layout = None
    language = None
    
    def __init__(self):
        super().__init__()
        
        self.setWindowTitle("virtual keyboard")
        self.resize(450, 150)
        
        self.unicode_fonts = UnicodeFonts()
        
        #self.language = None
        self.keys = None
        self.level_one_chars = None
        self.level_two_chars = None
        
        self.modifier = Qt.NoModifier
        
        self.ipa_keyboard = IPAKeyboard()
        
    def setLineEdit(self, lineEdit):
        self.lineEdit = lineEdit
        
    def drawKeyboard(self, layout, language):
        self.layout, self.language = layout, language
        
        self.level_one_chars, self.level_two_chars = self.getChars(language)
        self.keys = self.getKeys(layout)
        
        self.drawButtons(self.level_one_chars, self.keys)
        
        #self.enter = QPushButton("\u23ce", self)
        #self.enter.resize(50, 60)
        #self.enter.move(400, line_pos + line_width)
        
    def drawLevelOneKeyboard(self):
        self.destroyKeyboard()
        self.drawButtons(self.level_one_chars, self.keys)
    def drawLevelTwoKeyboard(self):
        self.destroyKeyboard()
        self.drawButtons(self.level_two_chars, self.keys)
        
    def drawButtons(self, chars, keys):
        button_sizes = self.getButtonSizes()
        button_colors = self.getButtonColors()
        
        for row in range(0, 5):
            
            row_offset = 0
            for i in range(len(chars[row])):
                
                if i > 0:
                    
                    button_a, button_b = button_sizes[row][i-1], button_sizes[row][i]
                    
                    if button_a > button_b:
                        if button_b >= 30:
                            offset = button_a / button_b
                            row_offset = row_offset + offset - 1
                
                #button = QPushButton(chars[row][i], self)
                button = QVkeybdPushButton(chars[row][i], self)
                self.unicode_fonts.applyFontToQWidgetFiltered(chars[row][i], button, ['hebrew'])
                button.resize(button_sizes[row][i], 30)
                button.move((i + row_offset)*30, row*30)
                
                r, g, b = button_colors[row][i]
                button.setBackgroundColor(QColor(r, g, b))
                
                button.show()
                
                self.connectButton(button, chars[row][i], keys[row][i])
            
    def connectButton(self, button, char, key):
        button.clicked.connect(functools.partial(self.printChar, char))
        self.keyPressedAny.connect(functools.partial(self.keyPressed, key, button))
        
    def printChar(self, char):
        if self.lineEdit:
            if char == '⇄':
                print("TAB PRESSED")
            elif char == '↑':
                event = QKeyEvent(QEvent.KeyPress, Qt.Key_Up, Qt.NoModifier)
                self.lineEdit.keyPressEvent(event)
            elif char == '↓':
                event = QKeyEvent(QEvent.KeyPress, Qt.Key_Down, Qt.NoModifier)
                self.lineEdit.keyPressEvent(event)
            elif char == '←':
                event = QKeyEvent(QEvent.KeyPress, Qt.Key_Left, Qt.NoModifier)
                self.lineEdit.keyPressEvent(event)
            elif char == '→':
                event = QKeyEvent(QEvent.KeyPress, Qt.Key_Right, Qt.NoModifier)
                self.lineEdit.keyPressEvent(event)
            elif char == '⏎':
                event = QKeyEvent(QEvent.KeyPress, Qt.Key_Enter, Qt.NoModifier)
                self.lineEdit.keyPressEvent(event)
            elif char == '⌫':
                event = QKeyEvent(QEvent.KeyPress, Qt.Key_Backspace, Qt.NoModifier)
                self.lineEdit.keyPressEvent(event)
            elif char == '⇧':
                # shift
                self.modifier = Qt.ShiftModifier
                self.drawLevelTwoKeyboard()
            elif char == '⇪':
                # capslock
                if self.modifier == Qt.ShiftModifier:
                    self.modifier = Qt.NoModifier
                    self.drawLevelOneKeyboard()
                elif self.modifier == Qt.NoModifier:
                    self.modifier = Qt.ShiftModifier
                    self.drawLevelTwoKeyboard()
            elif char == 'ctrl':
                print("CONTROL PRESSED")
            elif char == 'alt':
                print("ALT PRESSED")
            elif char == '⌘':
                print("WIndows key pressed")
            elif char == '⌥':
                print("anykey pressed")
            else:
                if self.language == "ipa":
                    ipa_char = self.ipa_keyboard.analyzeInput(char)
                    if ipa_char:
                        event = QKeyEvent(QEvent.KeyPress, Qt.Key_Backspace, Qt.NoModifier)
                        self.lineEdit.keyPressEvent(event)
                        
                        char = ipa_char
                
                self.lineEdit.appendText(char)
        else:
            print(char)
        
    def keyPressed(self, key, button, event):
        if event == key:
            button.animateClick()
        
    def keyPressEvent(self, e):
        
        if e.key() == Qt.Key_Return:
            pass
        elif e.key() == Qt.Key_Escape:
            pass
        elif e.key() >= Qt.Key_F1 and e.key() <= Qt.Key_F12:
            pass
        else:
            self.keyPressedAny.emit(e.key())
        
    def getChars(self, language):
        if language == "german":
            return self.getGermanChars(), self.getLevel2GermanChars()
        elif language == "greek":
            return self.getGreekChars(), self.getLevel2GreekChars()
        elif language == "hebrew":
            return self.getHebrewChars(), self.getLevel2HebrewChars()
        elif language == "arabic":
            return self.getArabicChars(), self.getLevel2ArabicChars()
        elif language == "hindi":
            return self.getDevanagariChars(), self.getLevel2DevanagariChars()
        elif language == "futhark":
            return self.getFutharkChars(), self.getLevel2FutharkChars()
        elif language == "ipa":
            return self.getGermanChars(), self.getLevel2GermanChars()
        else:
            return self.getHebrewChars(), self.getLevel2HebrewChars()
        
    def getGreekChars(self):
        return [["`", "1", "2", "3", "4", "5", "6", "7", "8", "9", "0", "-", "=", "\u232b"],
                ["⇄", ";", "ς", "ε", "ρ", "τ", "υ", "θ", "ι", "ο", "π", "[", "]", ""],
                ["\u21ea", "α", "σ", "δ", "φ", "γ", "η", "ξ", "κ", "λ", "´", "'", "\u23ce"],
                ["\u21E7", "", "ζ", "χ", "ψ", "ω", "β", "ν", "μ", ",", ".", "/", "\u21E7"],
                ["ctrl", "\u2318", "alt", " ", "←", "↓", "↑", "→", "alt", "\u2325", "ctrl"]]
    def getLevel2GreekChars(self):
        return [["`", "1", "2", "3", "4", "5", "6", "7", "8", "9", "0", "-", "=", "\u232b"],
                ["⇄", ";", "Σ", "Ε", "Ρ", "Τ", "Υ", "Θ", "Ι", "Ο", "Π", "[", "]", ""],
                ["\u21ea", "Α", "Σ", "Δ", "Φ", "Γ", "Η", "Ξ", "Κ", "Λ", "΄", "'", "\u23ce"],
                ["\u21E7", "", "Ζ", "Χ", "Ψ", "Ω", "Β", "Ν", "Μ", ",", ".", "/", "\u21E7"],
                ["ctrl", "\u2318", "alt", " ", "←", "↓", "↑", "→", "alt", "\u2325", "ctrl"]]
        
    def getHebrewChars(self):
        return [[";", "1", "2", "3", "4", "5", "6", "7", "8", "9", "0", "-", "=", "\u232b"],
                ["⇄", "/", "'", "ק", "ר", "א", "ט", "ו", "ן", "ם", "פ", "]", "[", ""],
                ["\u21ea", "ש", "ד", "ג", "כ", "ע", "י", "ח", "ל", "ך", "ף", ",", "\u23ce"],
                ["\u21E7", "", "ז", "ס", "ב", "ה", "נ", "מ", "צ", "ת", "ץ", ".", "\u21E7"],
                ["ctrl", "\u2318", "alt", " ", "←", "↓", "↑", "→", "alt", "\u2325", "ctrl"]]
    def getLevel2HebrewChars(self):
        return [[";", "1", "2", "3", "4", "5", "6", "7", "8", "9", "0", "-", "=", "\u232b"],
                ["⇄", "Q", "W", "E", "R", "T", "Y", "U", "I", "O", "P", "]", "[", ""],
                ["\u21ea", "A", "S", "D", "F", "G", "H", "J", "K", "L", ";", "'", "\u23ce"],
                ["\u21E7", "", "Z", "X", "C", "V", "B", "N", "M", ",", ".", "/" , "\u21E7"],
                ["ctrl", "\u2318", "alt", " ", "←", "↓", "↑", "→", "alt", "\u2325", "ctrl"]]
        
    def getGermanChars(self):
        return [["^", "1", "2", "3", "4", "5", "6", "7", "8", "9", "0", "ß", "´", "\u232b"],
                ["⇄", "q", "w", "e", "r", "t", "z", "u", "i", "o", "p", "ü", "+", "#"],
                ["\u21ea", "a", "s", "d", "f", "g", "h", "j", "k", "l", "ö", "ä", "\u23ce"],
                ["\u21E7", "<", "y", "x", "c", "v", "b", "n", "m", ",", "." ,"-", "\u21E7"],
                ["ctrl", "\u2318", "alt", " ", "←", "↓", "↑", "→", "agr", "\u2325", "ctrl"]]
        
    def getLevel2GermanChars(self):
        return [["°", "!", "\"", "§", "$", "%", "\u0038", "/", "(", ")", "=", "?", "`", "\u232b"],
                ["⇄", "Q", "W", "E", "R", "T", "Z", "U", "I", "O", "P", "Ü", "*"],
                ["\u21ea", "A", "S", "D", "F", "G", "H", "J", "K", "L", "Ö", "Ä", "'"],
                ["\u21E7", ">", "Y", "X", "C", "V", "B", "N", "M", ";", ":" ,"_", "\u21E7"],
                ["ctrl", "\u2318", "alt", " ", "←", "↓", "↑", "→", "agr", "\u2325", "ctrl"]]
    
    def getArabicChars(self):
        return [["ذ", "١", "٢", "٣", "٤", "٥", "٦", "٧", "٨", "٩", "٠", "~", "!", "\u232b"],
                ["⇄", "ض", "ص", "ث", "ق", "ف", "غ", "ع", "ه", "خ", "ح", "ج", "د", "\\"],
                ["\u21ea", "ش", "س", "ي", "ب", "ل", "ا", "ت", "ن", "م", "ك", "ط", "\u23ce"],
                ["\u21E7", "ئ", "ء", "ؤ", "ر", "لا", "ى", "ة", "و", "ز", "ظ" ,"ـ", "\u21E7"],
                ["ctrl", "\u2318", "alt", " ", "←", "↓", "↑", "→", "alt", "\u2325", "ctrl"]]
    def getLevel2ArabicChars(self):
        return [["ّ", "1", "2", "3", "4", "5", "6", "7", "8", "9", "0", "°", "+", "\u232b"],
                ["⇄", "ََ", "ً", "ُ", "ٌ", "ﻹ", "إ", "`", "÷", "×", "؛", "<", ">", ""],
                ["\u21ea", "ِ", "ٍ", "]", "[", "ﻷ", "أ", "ـ", "،", "/", ":", "", "\u23ce"],
                ["\u21E7", "~", "ْ", "}", "{", "ﻵ", "آ", "'", ",", ".", "؟" ,"ـ", "\u21E7"],
                ["ctrl", "\u2318", "alt", " ", "←", "↓", "↑", "→", "alt", "\u2325", "ctrl"]]
        
    def getDevanagariChars(self):
        return [["ॊ", "1", "2", "3", "4", "5", "6", "7", "8", "9", "0", "-", "ृ", "\u232b"],
                ["⇄", "ौ", "ै", "ा", "ी", "ू", "ब", "ह", "ग", "द", "ज", "ड", "ड़", "़"],
                ["\u21ea", "ो", "े", "्", "ि", "ु", "प", "र", "क", "त", "च", "ट", "\u23ce"],
                ["\u21E7", "ॆ", "ं", "म", "न", "व", "ल", "स", ",", ".", "य" ,"", "\u21E7"],
                ["ctrl", "\u2318", "alt", " ", "←", "↓", "↑", "→", "alt", "\u2325", "ctrl"]]
    
    def getLevel2DevanagariChars(self):
        return [["", "", "", "", "", "", "", "", "", "", "", "", "", "\u232b"],
                ["⇄", "", "", "", "", "", "", "", "", "", "", "", "", ""],
                ["\u21ea", "", "", "", "", "", "", "", "", "", "", "", "\u23ce"],
                ["\u21E7", "", "", "", "", "", "", "", "", "", "" ,"ـ", "\u21E7"],
                ["ctrl", "\u2318", "alt", " ", "←", "↓", "↑", "→", "alt", "\u2325", "ctrl"]]
    
    def getFutharkChars(self):
        return [["ᛢ", "ᚨ", "\u16b1", "", "", "", "", "", "", "", "", "", "", "\u232b"],
                ["⇄", "", "", "", "", "", "", "", "", "", "", "", "", ""],
                ["\u21ea", "", "", "", "", "", "", "", "", "", "", "", "\u23ce"],
                ["\u21E7", "", "", "", "", "", "", "", "", "", "" ,"ـ", "\u21E7"],
                ["ctrl", "\u2318", "alt", " ", "←", "↓", "↑", "→", "alt", "\u2325", "ctrl"]]
    
    def getLevel2FutharkChars(self):
        return [["", "", "", "", "", "", "", "", "", "", "", "", "", "\u232b"],
                ["⇄", "", "", "", "", "", "", "", "", "", "", "", "", ""],
                ["\u21ea", "", "", "", "", "", "", "", "", "", "", "", "\u23ce"],
                ["\u21E7", "", "", "", "", "", "", "", "", "", "" ,"ـ", "\u21E7"],
                ["ctrl", "\u2318", "alt", " ", "←", "↓", "↑", "→", "alt", "\u2325", "ctrl"]]
    
    "Template for copying it if you want to make new layouts"
    def getCharsTemplate(self):
        return [["", "", "", "", "", "", "", "", "", "", "", "", "", "\u232b"],
                ["⇄", "", "", "", "", "", "", "", "", "", "", "", "", ""],
                ["\u21ea", "", "", "", "", "", "", "", "", "", "", "", "\u23ce"],
                ["\u21E7", "", "", "", "", "", "", "", "", "", "" ,"ـ", "\u21E7"],
                ["ctrl", "\u2318", "alt", " ", "←", "↓", "↑", "→", "alt", "\u2325", "ctrl"]]
    
    def getButtonSizes(self):
        return [[30, 30, 30, 30, 30, 30, 30, 30, 30, 30, 30, 30, 30, 60],
                [40, 30, 30, 30, 30, 30, 30, 30, 30, 30, 30, 30, 30, 50],
                [50, 30, 30, 30, 30, 30, 30, 30, 30, 30, 30, 30, 70],
                [40, 30, 30, 30, 30, 30, 30, 30, 30, 30, 30, 30, 80],
                [30, 30, 30, 150, 30, 30, 30, 30, 30, 30, 30]]
    
    def getKeys(self, layout):
        if layout == "qwertz":
            return self.getQwertzKeys()
        elif layout == "neo":
            return self.getNeoKeys()
        else:
            return self.getQwertzKeys()
        
    def getQwertzKeys(self):
        return [[16781906, Qt.Key_1, Qt.Key_2, Qt.Key_3, Qt.Key_4, Qt.Key_5, Qt.Key_6, Qt.Key_7, Qt.Key_8, Qt.Key_9, Qt.Key_0, Qt.Key_ssharp, 16781905, Qt.Key_Backspace],
                [Qt.Key_Tab, Qt.Key_Q, Qt.Key_W, Qt.Key_E, Qt.Key_R, Qt.Key_T, Qt.Key_Z, Qt.Key_U, Qt.Key_I, Qt.Key_O, Qt.Key_P, Qt.Key_Udiaeresis, Qt.Key_Plus, Qt.Key_NumberSign],
                [Qt.Key_CapsLock, Qt.Key_A, Qt.Key_S, Qt.Key_D, Qt.Key_F, Qt.Key_G, Qt.Key_H, Qt.Key_J, Qt.Key_K, Qt.Key_L, Qt.Key_Odiaeresis, Qt.Key_Adiaeresis, Qt.Key_Return],
                [Qt.Key_Shift, Qt.Key_Less, Qt.Key_Y, Qt.Key_X, Qt.Key_C, Qt.Key_V, Qt.Key_B, Qt.Key_N, Qt.Key_M, Qt.Key_Comma, Qt.Key_Period, Qt.Key_Minus, -1],
                [Qt.Key_Control, Qt.Key_Meta, Qt.Key_Alt, Qt.Key_Space,  Qt.Key_Left, Qt.Key_Down, Qt.Key_Up, Qt.Key_Right, Qt.Key_AltGr, -1, -1]]
    
    def getNeoKeys(self):
        return [[16781906, Qt.Key_1, Qt.Key_2, Qt.Key_3, Qt.Key_4, Qt.Key_5, Qt.Key_6, Qt.Key_7, Qt.Key_8, Qt.Key_9, Qt.Key_0, Qt.Key_Minus, 16781905, Qt.Key_Backspace],
                [Qt.Key_Tab, Qt.Key_X, Qt.Key_V, Qt.Key_L, Qt.Key_C, Qt.Key_W, Qt.Key_K, Qt.Key_H, Qt.Key_G, Qt.Key_F, Qt.Key_Q, Qt.Key_ssharp, Qt.Key_Plus, Qt.Key_NumberSign],
                [Qt.Key_CapsLock, Qt.Key_U, Qt.Key_I, Qt.Key_A, Qt.Key_E, Qt.Key_O, Qt.Key_S, Qt.Key_N, Qt.Key_R, Qt.Key_T, Qt.Key_D, Qt.Key_Y, Qt.Key_Return],
                [Qt.Key_Shift, Qt.Key_Less, Qt.Key_Udiaeresis, Qt.Key_Odiaeresis, Qt.Key_Adiaeresis, Qt.Key_P, Qt.Key_Z, Qt.Key_B, Qt.Key_M, Qt.Key_Comma, Qt.Key_Period, Qt.Key_Minus, -1],
                [Qt.Key_Control, Qt.Key_Meta, Qt.Key_Alt, Qt.Key_Space,  Qt.Key_Left, Qt.Key_Down, Qt.Key_Up, Qt.Key_Right, Qt.Key_AltGr, -1, -1]]
    
    def getButtonColors(self):
        a = [255, 255, 255]
        b = [200, 200, 200]
        c = a
        d = b
        e = b
        f = a
        g = b
        h = a
        
        x = [127, 127, 127]
        z = [145, 145, 145]
        return [[a, a, a, b, c, d, d, e, e, f, g, h, h, z],
                [z, a, b, c, d, d, e, e, f, g, h, h, h, h],
                [z, a, b, c, x, d, e, x, f, g, h, h, z],
                [z, a, a, b, c, d, d, e, e, f, g, h, z],
                [z, z, z, z, z, z, z, z, z, z, z]]
    
    def destroyKeyboard(self):
        for button in self.findChildren(QVkeybdPushButton):
            button.clicked.disconnect()
            button.deleteLater()
        
        self.keyPressedAny.disconnect()