tro*_*rau 9 python qt pyqt command-line-arguments pyside
我正在写一个新的PyQt应用程序.我正在尝试使用尽可能多的PyQt API来完成与程序和ui相关的所有操作,以此来提高我对PyQt和Qt的了解.
我的问题是,PyQt/Qt中是否有一个API来优雅地处理命令行参数解析?
到目前为止我的研究已经出现:
那么PyQt应用程序通常如何处理呢?或者是opt_parser/argparse的方式去?
这远不是一个很好的解决方案......
#!/usr/bin/python
# -*- coding: utf-8 -*-
import sys, argparse
from PyQt4 import QtGui
def main(argv):
app = QtGui.QApplication(argv) # QApplication eats argv in constructor
# We can get a QStringList out of QApplication of those arguments it
# didn't decide were reserved by Qt.
argv2 = app.arguments()
# now we need to turn them back into something that optparse/argparse
# can understand, since a QStringList is not what it wants
argv3 = []
for i in argv2:
argv3.append(str(i))
# now we can pass this to optparse/argparse
process_args(argv3)
# dummy app
mw = QtGui.QMainWindow()
mw.show()
sys.exit(app.exec_())
def process_args(argv):
parser = argparse.ArgumentParser(description='PyQt4 argstest',
add_help=False)
# we now have to add all of the options described at
# http://qt-project.org/doc/qt-4.8/qapplication.html#QApplication
# but have them do nothing - in order to have them show up in the help list
# add this to the list if Qt is a debug build (How to detect this?)
parser.add_argument("-nograb", action=ignore,
help="don't grab keyboard/mouse for debugging")
# add these to the list if Qt is a debug build for X11
parser.add_argument("-dograb", action=ignore,
help="grab keyboard/mouse for debugging")
parser.add_argument("-sync", action=ignore,
help="run in synchronous mode for debugging")
# add all the standard args that Qt will grab on all platforms
parser.add_argument("-reverse", action=ignore,
help="run program in Right-to-Left mode")
# an example -- there are 10 such items in the docs for QApplication
# then we need to figure out if we're running on X11 and add these
parser.add_argument("-name", action=ignore,
help="sets the application name")
# an example -- there are 13 such items in the docs
# reimplement help (which we disabled above) so that -help works rather
# than --help; done to be consistent with the style of args Qt wants
parser.add_argument("-h", "-help", action='help',
help="show this help message and exit")
parser.parse_args(argv[1:])
class ignore(argparse.Action):
# we create an action that does nothing, so the Qt args do nothing
def __call__(self, parser, namespace, values, option_string=None):
pass
if __name__ == "__main__":
main(sys.argv)
Run Code Online (Sandbox Code Playgroud)
这里最好的解决方案是使用argparse模块的parse_known_args()方法(docs)来首先处理非Qt命令行选项.配置ArgumentParser-it只是更改您调用的方法,并在返回时为您提供元组而不是单个对象.这给你两全其美.
一个简单的例子,它只捕获了几个Qt 4.8参数和其他几个参数,但给出了一般的想法.
# my_script.py
import argparse
from PyQt4 import QtGui # this will work with PySide.QtGui, too
def process_cl_args():
parser = argparse.ArgumentParser()
parser.add_argument('-s', '--swallow', action='store') # optional flag
parser.add_argument('holy_hand_grenade', action='store') # positional argument
parsed_args, unparsed_args = parser.parse_known_args()
return parsed_args, unparsed_args
if __name__ == '__main__':
parsed_args, unparsed_args = process_cl_args()
# QApplication expects the first argument to be the program name.
qt_args = sys.argv[:1] + unparsed_args
app = QtGui.QApplication(qt_args)
# ... the rest of your handling: `sys.exit(app.exec_())`, etc.
Run Code Online (Sandbox Code Playgroud)
假设你这样运行:
$ python my_script.py -dograb --swallow=unladen 3 -style cde
Run Code Online (Sandbox Code Playgroud)
然后,parsed_args将具有通常Namespace与holy_hand_grenade设置为3和--swallow设置'unladen',同时unparsed_args将有一个简单的列表:['-dograb', '-style,' 'cde'].这反过来又可以正常传递到QApplication与来自包括节目名称的sys.argv[0](感谢马尔钦的指出这一点).我们sys.argv[:1]用来获取用于连接的数组unparsed_args; 你也可以这样做[sys.argv[0]]
除此之外,这还允许您设置应用程序以指定是否启动Qt UI,作为命令行运行,运行单元测试等等,如果您愿意的话.首先处理非Qt(或其他任何)参数更好,因为它不会argparse依赖于您正在使用的设置,反之亦然.
如果您使用( optparse if < ),请使用argparse,该包不必特定于 PyQt 来处理命令行选项。Python 2.72.7