热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

pyqt练习x3.11

#!usrbinenvpython#-*-coding:utf-8-*-######################################################

#!/usr/bin/env python

# -*- coding: utf-8 -*-

 

########################################################################################

#                                                                                      #

# Copyright (c) 2009 Jakob Kummerow                          #

#                                                                                      #

# This program is free software; you can redistribute it and/or modify it under        #

# the terms of the GNU General Public License as published by the Free Software        #

# Foundation; either version 3 of the License, or (at your option) any later           #

# version.                                                                             #

#                                                                                      #

# This program is distributed in the hope that it will be useful, but WITHOUT ANY      #

# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A      #

# PARTICULAR PURPOSE. See the GNU General Public License for more details.             #

#                                                                                      #

# You should have received a copy of the GNU General Public License along with         #

# this program.  If not, see .                           #

#                                                                                      #

########################################################################################

 

 

"""

Future ideas:

- auto-indenting: automatically increase/decrease indentation level. --> when?

- send further commands to Hugs without restarting --> major change, might need threads

- support GHCI --> would that be useful?

"""

 

import sys, os, re

from subprocess import Popen, PIPE

from tempfile import NamedTemporaryFile

from PyQt4.QtGui import * #@UnusedWildImport

from PyQt4.QtCore import * #@UnusedWildImport

 

fileFilter = "Haskell source files (*.hs);;All files (*.*)"

settingsFileName = ".config/hugsgui.conf"

fontfamily = "DejaVu Sans Mono"

 

class EditBox(QTextEdit):

 

def __init__(self, parent=None, defaultText=""):

QTextEdit.__init__(self)

self.setTabChangesFocus(False)

self.setAcceptRichText(False)

self.defaultText = defaultText

self.dirty = False

self.loadedFile = False

self.initialState()

self.connect(self, SIGNAL("textChanged()"), self.textChangedHandler)

# we need this to prevent the cursor from jumping back to the system‘s default font

self.connect(self, SIGNAL("currentCharFormatChanged(const QTextCharFormat&)"), self.resetCurrentCharFormat)

self.errorline = []

self.ffont = None

 

def clearInitially(self):

self.clear()

self.setTextColor(self.palette().color(QPalette.Active, QPalette.Text))

self.neverUsed = False

self.resetFont()

 

def initialState(self):

self.neverUsed = True

self.setTextColor(self.palette().color(QPalette.Disabled, QPalette.Text))

self.setPlainText(self.defaultText)

 

def highlightError(self, linenumber):

block = self.document().findBlockByLineNumber(linenumber)

format = block.blockFormat()

format.setBackground(QBrush(QColor(255, 128, 128, 255)))

cursor = self.textCursor()

cursor.setPosition(block.position())

cursor.setBlockFormat(format)

self.errorline += [block]

 

def resetErrorHighlight(self):

for line in self.errorline:

format = line.blockFormat()

format.clearBackground()

cursor = self.textCursor()

if line.position() < self.document().characterCount():

cursor.setPosition(line.position())

cursor.setBlockFormat(format)

self.errorline = []

 

def keyPressEvent(self, e):

if self.neverUsed:

self.clearInitially()

 

if e.key() == Qt.Key_Backtab:

# unindent, either current line only or all selected lines

maincursor = self.textCursor()

if not maincursor.hasSelection():

maincursor.movePosition(QTextCursor.StartOfBlock)

line = str(self.document().findBlockByNumber(maincursor.blockNumber()).text().toUtf8())

whitespace = re.match(r"(\s{0,2})", line).group(1)

for i in range(len(whitespace)): #@UnusedVariable

maincursor.deleteChar()

else:

block = self.document().findBlock(maincursor.selectionStart())

while True:

whitespace = re.match(r"(\s{0,2})", str(block.text().toUtf8())).group(1)

cursor = self.textCursor() 

cursor.setPosition(block.position())

for i in range(len(whitespace)): #@UnusedVariable

cursor.deleteChar()

if block.contains(maincursor.selectionEnd()):

break

block = block.next()

e.accept()

elif e.key() == Qt.Key_Tab:

# indent, either current line only or all selected lines

maincursor = self.textCursor()

if not maincursor.hasSelection():

maincursor.insertText("  ")

else:

block = self.document().findBlock(maincursor.selectionStart())

while True:

cursor = self.textCursor() 

cursor.setPosition(block.position())

cursor.insertText("  ")

if block.contains(maincursor.selectionEnd()):

break

block = block.next()

e.accept()

elif e.key() == Qt.Key_Return:

# copy whitespace from the beginning of the previous line

cursor = self.textCursor()

block = self.document().findBlockByNumber(cursor.blockNumber())

whitespace = re.match(r"(\s*)", str(block.text().toUtf8())).group(1)

QTextEdit.keyPressEvent(self, e)

cursor = self.textCursor()

format = cursor.blockFormat()

format.clearBackground()

cursor.setBlockFormat(format)

cursor.insertText(whitespace)

else:

QTextEdit.keyPressEvent(self, e)

 

def focusInEvent(self, e):

if self.neverUsed and e.reason() != Qt.ActiveWindowFocusReason:

self.clearInitially()

QTextEdit.focusInEvent(self, e)

 

def focusOutEvent(self, e):

if self.loadedFile == False and self.toPlainText() == "":

self.initialState()

QTextEdit.focusOutEvent(self, e)

 

def mousePressEvent(self, e):

if self.neverUsed:

self.clearInitially()

QTextEdit.mousePressEvent(self, e)

 

def toPlainText(self):

if self.neverUsed:

return ""

return str(QTextEdit.toPlainText(self).toUtf8())

 

def textChangedHandler(self):

if self.loadedFile == False and (self.neverUsed or self.toPlainText() == ""):

self.dirty = False

else:

self.dirty = True

 

def resetFont(self, fOnt=None):

if font != None:

self.ffont = font

newFormat = QTextCharFormat()

if self.ffont == None:

newFormat.setFontFamily(fontfamily)

else:

newFormat.setFont(self.ffont)

cursor = self.textCursor()

cursor.movePosition(QTextCursor.Start)

cursor.movePosition(QTextCursor.End, QTextCursor.KeepAnchor)

cursor.mergeCharFormat(newFormat)

self.setCurrentCharFormat(cursor.charFormat())

 

def resetCurrentCharFormat(self):

format = self.textCursor().charFormat()

if self.ffont == None:

format.setFontFamily(fontfamily)

else:

format.setFont(self.ffont)

self.setCurrentCharFormat(format)

 

 

class HugsGUI(QMainWindow):

 

def __init__(self, parent=None):

QMainWindow.__init__(self, parent)

self.setWindowTitle(‘Hugs GUI‘)

 

self.editTextBox = EditBox(self, "Function definition file")

self.commandTextBox = EditBox(self, "Commands for interactive Hugs session")

 

self.outputTextBox = EditBox(self)

self.outputTextBox.setReadOnly(True)

self.outputTextBox.neverUsed = False

 

self.splitter = QSplitter(Qt.Vertical)

self.splitter.addWidget(self.editTextBox)

self.splitter.addWidget(self.commandTextBox)

self.splitter.addWidget(self.outputTextBox)

self.setCentralWidget(self.splitter)

 

toolbar = self.addToolBar("Main")

 

newAction = QAction("New", self)

newAction.setShortcut("Ctrl+N")

newAction.setToolTip("Create a new file (Ctrl+N)")

self.connect(newAction, SIGNAL("triggered()"), self.newFile)

toolbar.addAction(newAction)

 

openAction = QAction("Open...", self)

openAction.setShortcut("Ctrl+O")

openAction.setToolTip("Open file (Ctrl+O)")

self.connect(openAction, SIGNAL("triggered()"), self.openFile)

toolbar.addAction(openAction)

 

saveAction = QAction("Save...", self)

saveAction.setShortcut("Ctrl+S")

saveAction.setToolTip("Save file (Ctrl+S)")

self.connect(saveAction, SIGNAL("triggered()"), self.saveFile)

toolbar.addAction(saveAction)

 

saveAsAction = QAction("Save as...", self)

self.connect(saveAsAction, SIGNAL("triggered()"), self.saveFileAs)

toolbar.addAction(saveAsAction)

 

toolbar.addSeparator()

runAction = QAction("Run!", self)

runAction.setShortcut("F9")

runAction.setToolTip("Run (F9)")

self.connect(runAction, SIGNAL("triggered()"), self.runHugs)

toolbar.addAction(runAction)

 

self.autoSaveAction = QAction("AutoSave before running", self)

self.autoSaveAction.setCheckable(True)

self.autoSaveAction.setToolTip("Whether the current document should automatically be saved before executing it.")

 

self.interactiveSaveAction = QAction("Save commands for interactive mode", self)

self.interactiveSaveAction.setCheckable(True)

self.interactiveSaveAction.setToolTip("Whether the current command list for the interactive session should be saved on program exit.")

 

fontAction = QAction("Choose Font...", self)

fontAction.setToolTip("Show a dialog that allows choosing the font to use")

self.connect(fontAction, SIGNAL("triggered()"), self.chooseFont)

 

optionsbutton = QToolButton()

optionsbutton.setPopupMode(QToolButton.InstantPopup)

optionsbutton.setText("Options")

options = QMenu("Options", optionsbutton)

options.addAction(self.autoSaveAction)

options.addAction(self.interactiveSaveAction)

options.addAction(fontAction)

optionsbutton.setMenu(options)

toolbar.addSeparator()

toolbar.addWidget(optionsbutton)

 

self.filename = ""

self.ffont = None

 

self.loadSettings()

 

def closeEvent(self, event):

if self.editTextBox.dirty:

reply = QMessageBox.question(self, "Question", "Would you like to save your changes before quitting?",

QMessageBox.Save, QMessageBox.Discard, QMessageBox.Cancel)

if reply == QMessageBox.Save:

self.saveFile()

elif reply == QMessageBox.Cancel:

event.ignore()

return

event.accept()

self.saveSettings()

 

def runHugs(self):

code = self.editTextBox.toPlainText()

if code != "":

if (not self.autoSaveAction.isChecked()) or self.filename == "":

hsfile = NamedTemporaryFile(delete=False)

hsfilepath = hsfile.name

hsfile.file.write(code)

hsfile.file.close()

else:

if self.editTextBox.dirty:

self.saveFile()

hsfilepath = self.filename

else:

hsfilepath = ""

self.outputTextBox.setText("")

echo = self.commandTextBox.toPlainText()

if echo == "":

echo = ":q"

else:

echo = ":set +t\n" + echo

inputfile = NamedTemporaryFile(delete=False)

inputfilepath = inputfile.name

inputfile.file.write(echo)

inputfile.file.close()

if hsfilepath != "":

execstring = str("hugs " + hsfilepath + " < " + inputfilepath)

hugs_out = Popen(execstring, shell=True, stdout=PIPE)

else:

execstring = str("hugs < " + inputfilepath)

hugs_out = Popen(execstring, shell=True, stdout=PIPE)

hugs_out.wait()

show = 0

linenumber = 0

self.editTextBox.resetErrorHighlight()

self.commandTextBox.resetErrorHighlight()

while True:

l = hugs_out.stdout.readline()

if l.rstrip().endswith("> [Leaving Hugs]"): 

break

if l.startswith("Type :? for help") or l.startswith("Haskell 98 mode"):

show = 1

elif show == 1:

show = 2

if show == 2 and re.match(r"(.*?)> \1>", l) is not None:

l = l.partition("> ")[2]

show = 3

if show >= 2:

self.outputTextBox.append(l.strip())

if l.startswith("Hugs> ") or l.startswith("Main> "):

if l.startswith("Hugs> ERROR") or l.startswith("Main> ERROR"):

self.commandTextBox.highlightError(linenumber)

linenumber += 1

if l.startswith("ERROR"):

self.highlightError(l)

# clean up

if self.filename == "" and hsfilepath != "":

os.remove(hsfilepath)

os.remove(inputfilepath)

 

def highlightError(self, line):

linenumber = int(re.match(r"ERROR \".*?\":(\d+) ", line).group(1)) - 1

self.editTextBox.highlightError(linenumber)

 

def newFile(self):

if self.editTextBox.dirty:

reply = QMessageBox.question(self, "Question", "Would you like to save your changes before creating a new file?",

QMessageBox.Save, QMessageBox.Discard, QMessageBox.Cancel)

if reply == QMessageBox.Save:

self.saveFile()

elif reply == QMessageBox.Cancel:

return

self.editTextBox.clearInitially()

self.editTextBox.dirty = False

self.editTextBox.loadedFile = False

self.filename = ""

 

def openFile(self):

if self.editTextBox.dirty:

reply = QMessageBox.question(self, "Question", "Would you like to save your changes before loading another file?",

QMessageBox.Save, QMessageBox.Discard, QMessageBox.Cancel)

if reply == QMessageBox.Save:

self.saveFile()

elif reply == QMessageBox.Cancel:

return

filename = QFileDialog.getOpenFileName(self, "Open file", QString(), fileFilter)

if filename != "":

self.filename = filename

self.editTextBox.clearInitially()

with open(filename) as f:

self.editTextBox.setPlainText("".join(f.readlines()))

self.editTextBox.dirty = False

self.editTextBox.loadedFile = True

 

def saveFileAs(self):

filename = "" + QFileDialog.getSaveFileName(self, "Save file", "untitled.hs", fileFilter).toUtf8()

if filename != "":

self.filename = filename

self.saveFile()

 

def saveFile(self):

if self.filename == "":

self.saveFileAs()

else:

with open(self.filename, ‘w‘) as f:

f.write(self.editTextBox.toPlainText())

self.editTextBox.dirty = False

 

def chooseFont(self):

(selectedfont, ok) = QFontDialog.getFont(self.editTextBox.textCursor().charFormat().font(), self)

if ok:

self.ffont = selectedfont

self.setAllFonts()

 

def setAllFonts(self):

self.editTextBox.resetFont(self.ffont)

self.commandTextBox.resetFont(self.ffont)

self.outputTextBox.resetFont(self.ffont)

 

def saveSettings(self):

settingsfile = QDir.home().absoluteFilePath(settingsFileName)

settings = QSettings(settingsfile, QSettings.IniFormat)

settings.setValue("View/Size", self.size())

settings.setValue("View/Split", self.splitter.sizes())

settings.setValue("Settings/SaveOnRun", self.autoSaveAction.isChecked())

settings.setValue("Settings/SaveInteractive", self.interactiveSaveAction.isChecked())

if self.interactiveSaveAction.isChecked():

settings.setValue("Interactive/Commands", self.commandTextBox.toPlainText())

if self.ffont != None:

settings.setValue("Settings/Font", self.ffont)

 

def loadSettings(self):

settingsfile = QDir.home().absoluteFilePath(settingsFileName)

settings = QSettings(settingsfile, QSettings.IniFormat)

self.resize(settings.value("View/Size", QSize(800, 500)).toSize())

splits = settings.value("View/Split", [154, 154, 154]).toList()

for i in range(len(splits)):

(splits[i], ok) = splits[i].toInt() #@UnusedVariable

if splits[i] < 10:

splits[i] = 10

self.splitter.setSizes(splits)

self.autoSaveAction.setChecked(settings.value("Settings/SaveOnRun", True).toBool())

self.interactiveSaveAction.setChecked(settings.value("Settings/SaveInteractive", False).toBool())

if self.interactiveSaveAction.isChecked():

self.commandTextBox.clearInitially()

self.commandTextBox.setPlainText(settings.value("Interactive/Commands", "").toString())

settingsfont = settings.value("Settings/Font", None)

if not settingsfont == QVariant(None):

self.ffont = QFont(settingsfont)

self.setAllFonts()

 

if __name__ == ‘__main__‘:

app = QApplication(sys.argv)

 

mainwin = HugsGUI()

mainwin.show()

 

sys.exit(app.exec_())

 技术分享

pyqt练习x3.11


推荐阅读
  • 使用GDI的一些AIP函数我们可以轻易的绘制出简 ... [详细]
  • 深入理解OAuth认证机制
    本文介绍了OAuth认证协议的核心概念及其工作原理。OAuth是一种开放标准,旨在为第三方应用提供安全的用户资源访问授权,同时确保用户的账户信息(如用户名和密码)不会暴露给第三方。 ... [详细]
  • Python 异步编程:深入理解 asyncio 库(上)
    本文介绍了 Python 3.4 版本引入的标准库 asyncio,该库为异步 IO 提供了强大的支持。我们将探讨为什么需要 asyncio,以及它如何简化并发编程的复杂性,并详细介绍其核心概念和使用方法。 ... [详细]
  • 1.如何在运行状态查看源代码?查看函数的源代码,我们通常会使用IDE来完成。比如在PyCharm中,你可以Ctrl+鼠标点击进入函数的源代码。那如果没有IDE呢?当我们想使用一个函 ... [详细]
  • 本文介绍了一款用于自动化部署 Linux 服务的 Bash 脚本。该脚本不仅涵盖了基本的文件复制和目录创建,还处理了系统服务的配置和启动,确保在多种 Linux 发行版上都能顺利运行。 ... [详细]
  • Android 渐变圆环加载控件实现
    本文介绍了如何在 Android 中创建一个自定义的渐变圆环加载控件,该控件已在多个知名应用中使用。我们将详细探讨其工作原理和实现方法。 ... [详细]
  • 本文介绍如何通过Windows批处理脚本定期检查并重启Java应用程序,确保其持续稳定运行。脚本每30分钟检查一次,并在需要时重启Java程序。同时,它会将任务结果发送到Redis。 ... [详细]
  • 本文详细解析了Python中的os和sys模块,介绍了它们的功能、常用方法及其在实际编程中的应用。 ... [详细]
  • 本文介绍了在Windows环境下使用pydoc工具的方法,并详细解释了如何通过命令行和浏览器查看Python内置函数的文档。此外,还提供了关于raw_input和open函数的具体用法和功能说明。 ... [详细]
  • 优化ASM字节码操作:简化类转换与移除冗余指令
    本文探讨如何利用ASM框架进行字节码操作,以优化现有类的转换过程,简化复杂的转换逻辑,并移除不必要的加0操作。通过这些技术手段,可以显著提升代码性能和可维护性。 ... [详细]
  • python的交互模式怎么输出名文汉字[python常见问题]
    在命令行模式下敲命令python,就看到类似如下的一堆文本输出,然后就进入到Python交互模式,它的提示符是>>>,此时我们可以使用print() ... [详细]
  • CentOS7源码编译安装MySQL5.6
    2019独角兽企业重金招聘Python工程师标准一、先在cmake官网下个最新的cmake源码包cmake官网:https:www.cmake.org如此时最新 ... [详细]
  • Python自动化处理:从Word文档提取内容并生成带水印的PDF
    本文介绍如何利用Python实现从特定网站下载Word文档,去除水印并添加自定义水印,最终将文档转换为PDF格式。该方法适用于批量处理和自动化需求。 ... [详细]
  • 本文探讨了如何在给定整数N的情况下,找到两个不同的整数a和b,使得它们的和最大,并且满足特定的数学条件。 ... [详细]
  • 本文介绍如何使用Python进行文本处理,包括分词和生成词云图。通过整合多个文本文件、去除停用词并生成词云图,展示文本数据的可视化分析方法。 ... [详细]
author-avatar
平凡快乐的girl_819
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有