class MainForm(QMainWindow): """ Main window class for program """ def __init__(self, parent=None): super(MainForm, self).__init__(parent) self.setWindowTitle('Language Utilities') self.setWindowIcon(QIcon(r'.\tiles\python.png')) self.resize(400, 400) self.setWindowFlags(Qt.Window | Qt.CustomizeWindowHint | Qt.WindowTitleHint | Qt.WindowCloseButtonHint | Qt.WindowStaysOnTopHint) self.win = None self.dirs = None self.gaddag = None self.newlang = None self.log = None self.view = None self.inp = None self.chars = None self.logOutput = None self.lett2_check = None self.lett2 = None self.c_lett2 = False self.drop = None self.lang_combo = None self.txt_file = None self.p_file = None self.language = None self.multi_char_letts = None self.max_char_len = None self.multi_char = None self.gaddag = None self.instr = None self.set_UI() def set_UI(self): """ Set up main window """ self.win = QTabWidget() self.setCentralWidget(self.win) self.instr = QWidget() self.dirs = QWidget() self.gaddag = QWidget() self.win.addTab(self.instr, "Instructions") self.win.addTab(self.dirs, "Files") self.win.addTab(self.gaddag, "GADDAG") self.instrUI() self.dirsUI() self.gaddagUI() def instrUI(self): """ Set up Instructions tab """ inst = QTextEdit(self) inst.setReadOnly(True) inst.setMinimumHeight(100) with open("HTMLcreate.html") as myfile: # read html from file text = "".join(line.strip() for line in myfile) text = text[text.index("<"):] inst.setHtml(text) frame0 = QFrame(self) frame0.setFrameShape(QFrame.Panel) frame0.setFrameShadow(QFrame.Raised) hbox1 = QHBoxLayout() frame0.setLayout(hbox1) hbox1.addWidget(inst) vbox = QVBoxLayout() vbox.addWidget(frame0) self.instr.setLayout(vbox) self.centre() def dirsUI(self): """ Setup directory tab in main window """ instr = QTextEdit(self) instr.setReadOnly(True) instr.setMinimumHeight(200) instr.insertPlainText( "This section helps you to set up a new language.\n\n") instr.insertPlainText( "Insert the name of the language in the box below and " "a sub-directory of that name will be created with all " "required files which you will then need to amend and " "translate.\n\n") self.newlang = QLineEdit(self) createdir_btn = QPushButton('Create', self) createdir_btn.clicked.connect(self.create_dir) self.log = QTextEdit(self) self.log.setObjectName("Log") quit_btn = QPushButton('Quit', self) quit_btn.clicked.connect(self.quit_app) frame0 = QFrame(self) frame0.setMinimumHeight(240) frame0.setFrameShape(QFrame.Panel) frame0.setFrameShadow(QFrame.Raised) hbox1 = QHBoxLayout() frame0.setLayout(hbox1) hbox1.addWidget(instr) hbox2 = QHBoxLayout() hbox2.addWidget(QLabel("Enter name of new language")) hbox3 = QHBoxLayout() hbox3.addWidget(self.newlang) hbox3.addWidget(createdir_btn) hbox4 = QHBoxLayout() hbox4.addWidget(self.log) hbox5 = QHBoxLayout() hbox5.addStretch(1) hbox5.addWidget(quit_btn) vbox = QVBoxLayout() vbox.addStretch(1) vbox.addWidget(frame0) vbox.addLayout(hbox2) vbox.addLayout(hbox3) vbox.addLayout(hbox4) vbox.addLayout(hbox5) self.dirs.setLayout(vbox) self.centre() self.write_log(self.log, "Enter language name and press Create") def gaddagUI(self): """ Setup GADDAG tab in main window """ self.inp = QLineEdit(self) self.drop = QLabel("Drop file here") self.drop.setAlignment(Qt.AlignCenter) self.drop.setMinimumWidth(self.inp.frameGeometry().width()) self.view = TestListView(self.drop) self.view.setMaximumHeight(50) self.view.resize(self.drop.size()) self.view.setAttribute(Qt.WA_TranslucentBackground) self.view.dropped.connect(self.pictureDropped) self.view.enter.connect(lambda: self.set_background(1)) self.view.leave.connect(lambda: self.set_background(0)) self.chars = QLineEdit(self) browse = QPushButton("Browse", self) browse.clicked.connect(self.browse_file) self.lang_combo = QComboBox(self) self.lang_combo.addItems(self._get_langs("__init__.py")) self.lang_combo.setEditable(True) self.lang_combo.activated.connect(self.lang_choice) self.lett2_check = QCheckBox(self) self.lett2_check.stateChanged.connect(self.create_lett2) self.logOutput = QTextEdit(self) self.logOutput.setObjectName("Log") self.logOutput.setReadOnly(True) self.logOutput.setLineWrapMode(QTextEdit.WidgetWidth) self.logOutput.setMinimumHeight(200) create_btn = QPushButton('Create', self) create_btn.clicked.connect(self.create_file) save_btn = QPushButton('Save', self) save_btn.clicked.connect(self.save_file) quit_btn = QPushButton('Quit', self) quit_btn.clicked.connect(self.quit_app) self._set_layout(browse, create_btn, save_btn, quit_btn) def _set_layout(self, browse, create_btn, save_btn, quit_btn): """ Layout for tab """ vbox = QVBoxLayout() vbox.addStretch(1) frame1 = QFrame(self) frame1.setFrameShape(QFrame.Panel) frame1.setFrameShadow(QFrame.Raised) grid1 = QGridLayout() frame1.setLayout(grid1) grid1.setSpacing(10) grid1.setColumnMinimumWidth(3, 30) grid1.addWidget(QLabel("Enter filename or drag and drop in box below"), 0, 0, 1, 3) grid1.addWidget(self.inp, 1, 0, 1, 3) grid1.addWidget(browse, 1, 3, 1, 1) grid1.addWidget(self.drop, 2, 0, 1, 3) frame2 = QFrame(self) frame2.setFrameShape(QFrame.Panel) frame2.setFrameShadow(QFrame.Raised) grid2 = QGridLayout() frame2.setLayout(grid2) grid2.addWidget(QLabel("Choose language"), 3, 0, 1, 1) grid2.addWidget(self.lang_combo, 3, 1, 1, 3) grid2.addWidget(QLabel("or"), 4, 0) grid2.addWidget(QLabel("List multi-character letters"), 5, 0, 1, 1) grid2.addWidget(self.chars, 5, 1, 1, 3) frame3 = QFrame(self) frame3.setFrameShape(QFrame.Panel) frame3.setFrameShadow(QFrame.Raised) hbox = QHBoxLayout() frame3.setLayout(hbox) hbox.addWidget(QLabel("Create and save two letter words file (lett2)")) hbox.addWidget(self.lett2_check, 0, Qt.AlignRight) hbox1 = QHBoxLayout() hbox1.addWidget(self.logOutput) hbox2 = QHBoxLayout() hbox2.addStretch(1) hbox2.addWidget(create_btn) hbox2.addWidget(save_btn) hbox2.addWidget(quit_btn) vbox.addWidget(frame1) vbox.addWidget(frame2) vbox.addWidget(frame3) vbox.addLayout(hbox1) vbox.addLayout(hbox2) self.gaddag.setLayout(vbox) self.centre() self.write_log(self.logOutput, "Choose Text file") def centre(self): """ Centre window """ qr = self.frameGeometry() cp = QDesktopWidget().availableGeometry().center() qr.moveCenter(cp) self.move(qr.topLeft()) def create_dir(self): """ Create language directory and copy necessary files into it """ path = os.getcwd() subdir = path + '\\' + self.newlang.text() if os.path.isdir(subdir): self.write_log(self.log, "\nAlready a langauge of that name") else: try: os.mkdir(subdir) except OSError: print("Creation of the directory %s failed" % subdir) self.write_log( self.log, "\nCreation of the directory %s failed" % subdir) else: print("Successfully created the directory %s " % subdir) self.write_log( self.log, "\nSuccessfully created the directory %s " % subdir) self.copy_files(path, subdir) def copy_files(self, path, dest): """ Copy files into language directory """ files = [ "__init__.py", "alphabet.py", "Final_score.html", "Instructions.html", "scrabble_letters.png" ] self.write_log(self.log, "\nCopying files") for file in files: shutil.copy2(path + '\\' + "english" + '\\' + file, dest) if file == "alphabet.py": try: f = open(dest + '\\alphabet.py', 'r') lines = f.readlines() lines[0] = '""" Language develop """\n' f.close() f = open(dest + '\\alphabet.py', 'w') f.writelines(lines) f.close() except IOError: self.write_log(self.log, "\nProblem with alphabet.py") self.write_log(self.log, "\nCopying file: " + file) self.write_log(self.log, "\nAll files copied") @staticmethod def _get_langs(file): """ Return list of languages installed """ langs = [None] for root, _, files in os.walk(r'.'): # root, dirs, files if file in files and 'alphabet.py' in files: drc = os.path.basename(root) langs.append(drc) return langs def browse_file(self): """ Browse for text file to convert """ filename, _ = QFileDialog.getOpenFileName(self, 'Open file', '.', '*.txt') self.inp.setText(filename) if os.path.isfile(filename): self.write_log(self.logOutput, "\nText file: " + filename) self.txt_file = filename else: self.write_log(self.logOutput, "\nError: Text file is not a valid file.") def lang_choice(self, index): """ Get language from combo box """ self.language = self.lang_combo.itemText(index) self.write_log(self.logOutput, "\nLanguage: " + self.language) def create_lett2(self, state): """ Set create lett2 flag depending on state of check box """ if state == Qt.Checked: self.c_lett2 = True self.write_log(self.logOutput, "\nTwo letter words file will be created (lett2)") else: self.c_lett2 = False self.write_log(self.logOutput, "\nTwo letter words file will not be created") def create_file(self): """ Create GADDAG in memory """ if self.txt_file is None: self.write_log(self.logOutput, "\nError: No text file.") return if self.language is not None: self.write_log(self.logOutput, "\nCreating GADDAG.") self.create_from_file(self.txt_file, qalphabet.Alphabet(self.language)) self.write_log(self.logOutput, "\nGADDAG created in memory.") elif self.multi_char_letts is not None: self.multi_char_letts = self.chars.text().split() self.max_char_len = len(max(self.multi_char_letts, key=len)) self.multi_char = [s[0] for s in self.multi_char_letts] self.write_log(self.logOutput, "\nCreating GADDAG.") self.create_from_file(self.txt_file, self) self.write_log(self.logOutput, "\nGADDAG created in memory.") else: self.write_log( self.logOutput, "\nNo details of language given. " "Letters assumed to be single characters\n") self.create_from_file(self.txt_file, self) self.write_log(self.logOutput, "\nGADDAG created in memory.") def save_file(self): """ Save GADDAG """ filename, _ = QFileDialog.getSaveFileName(self, 'Save file', '.', '*.p') _, f_extension = os.path.splitext(filename) f_path, _ = os.path.split(filename) lett2_file = f_path + '\\lett2.txt' if not f_extension: filename = filename + '.p' try: self.gaddag.save(filename) except IOError as inst: self.write_log(self.logOutput, "\nError: " + str(inst) + " saving GADDAG") else: self.write_log(self.logOutput, "\nGADDAG saved: " + filename) if self.c_lett2: try: with open(lett2_file, 'w') as f: for item in self.lett2: f.write("%s\n" % item) except IOError as inst: self.write_log(self.logOutput, "\nError: " + str(inst) + " saving lett2") else: self.write_log(self.logOutput, "\nTwo letter words file saved: " + lett2_file) def pictureDropped(self, lst): """ Drag and drop files into listview """ for url in lst: if os.path.exists(url): self.inp.setText(url) self.txt_file = url self.write_log(self.logOutput, "\nText file: " + url) def set_background(self, state): """ Change background if drag on label """ if state == 0: self.drop.setStyleSheet( "background-color: qradialgradient(cx:0, cy:0," "radius: 1, fx:0.5, fy:0.5, stop:0 lightgray," "stop:1 #b17d7d);") if state == 1: self.drop.setStyleSheet( "background-color: qradialgradient(cx:1, cy:1," "radius: 1, fx:0.5, fy:0.5, stop:0 lightgray," "stop:1 #b17d7d);") @staticmethod def write_log(log, msg): """ Write to log """ log.moveCursor(QTextCursor.End) log.insertPlainText(msg) log.verticalScrollBar().setValue(log.verticalScrollBar().maximum()) @staticmethod def quit_app(): """ Quit application """ QApplication.instance().quit() def to_list(self, string): """ Convert string in alphabet to list of letters """ letters = [] if self.multi_char_letts is None or self.max_char_len == 1: letters = list(string) else: i = 0 while i < len(string): char = string[i] if char in self.multi_char: k = 1 while k < self.max_char_len: if string[i:i + k + 1] not in self.multi_char_letts: break char = string[i:i + k + 1] k += 1 letters.append(char) i += len(char) return letters @staticmethod def remove_diacritic(text): """ Accept a unicode string, and return a normal string (bytes in Python 3) without any diacritical marks. """ return unicodedata.normalize('NFKD', text).encode('ASCII', 'ignore') def create_from_file(self, filename, iaith): """ Create a GADDAG from a text file of a lexicon. If no filename is supplied then it will default to the WORDLIST_PATH setting. The text file should only have the words in the lexicon, one per line, with a blank line at the very end. Args: filename: An existing file-like object to read from. iaith: Instance of language class Alphabet """ self.gaddag = pygaddag.GADDAG() wordcount = 0 self.lett2 = [] self.write_log(self.logOutput, "\n") with open(filename, 'r', encoding="utf-8") as f: for word in f.readlines(): wordcount += 1 word = word.strip().lower() noaccent = self.remove_diacritic(word).decode() output = iaith.to_list(noaccent) if not noaccent.isalpha() or len(word) <= 1: self.write_log(self.logOutput, "{0}: {1}\r".format(wordcount, word)) else: if len(noaccent) == 2: self.lett2.append(noaccent) self.gaddag.add(output) if (wordcount % 100) == 0: self.write_log(self.logOutput, "{0}\r".format(wordcount))