在这篇文章中,我解释了如何检查在 Windows 会话中打开了多少 QGIS 项目。
这是缩短的代码:
import os
import subprocess
from os.path import basename
from PyQt4.QtGui import QMessageBox
def checkQgisProcesses(self):
try:
from subprocess import DEVNULL
except ImportError:
DEVNULL = os.open(os.devnull, os.O_RDWR)
res = subprocess.check_output('C:\Windows\System32\cmd.exe /c tasklist /FI "IMAGENAME eq qgis-bin.exe" -v 2>NUL', stdin=DEVNULL, stderr=DEVNULL, startupinfo = info)
...
def someOtherFunc(self):
self.checkQgisProcesses()
...
该代码使用tasklist
从 Windows 获取有关所有打开窗口的信息并过滤 QGIS 窗口标题。
我在 QGIS 插件的函数中使用此代码。
插件中还有另一个函数,我在其中调用了多个函数以subprocess
使用另一个程序 ( SAGA GIS
) 进行一些计算:
curv_PATH = plugin_pth + 'dem_curvature.bat'
subprocess.call(["C:\Windows\System32\cmd.exe", "/c", script_PATH], startupinfo = info)
subprocess.call(['gdalwarp', raster_dest_data + 'dem_gaussian.sdat', '-tr', cellsize, cellsize, '-r', 'bilinear', raster_dest_data + 'dem_res.tif' ], startupinfo = info)
subprocess.call(["C:\Windows\System32\cmd.exe", "/c", curv_PATH], startupinfo = info)
问题是这些subprocess
调用不再起作用。我在 QGIS python 控制台中没有收到特定错误。
当我发表评论self.checkQgisProcesses()
时,它再次起作用。
我认为问题在于DEVNULL
, stdin
,stderr
参数。
如何将它们设置回默认值?
更新
我错误地认为问题可能出在DEVNULL
声明上。显然问题在于使用subprocess.STARTUPINFO()
.
这是一个可重现的示例:
import os
from os.path import basename
import subprocess
SW_HIDE = 0
info = subprocess.STARTUPINFO()
info.dwFlags = subprocess.STARTF_USESHOWWINDOW
info.wShowWindow = SW_HIDE
def checkFirefoxProcesses():
try:
from subprocess import DEVNULL
except ImportError:
DEVNULL = os.open(os.devnull, os.O_RDWR)
res = subprocess.check_output('C:\Windows\System32\cmd.exe /c tasklist /FI "IMAGENAME eq firefox.exe" -v 2>NUL', stdin=DEVNULL, stderr=DEVNULL, startupinfo = info)
print res
def helloWorldToText():
subprocess.call(["C:\Windows\System32\cmd.exe", "/c", r"d:\\hello_world.bat"], startupinfo = info)
checkFirefoxProcesses()
helloWorldToText()
这是来自的代码hello_world.bat
:
REM @ECHO OFF
ECHO Hello World! > d:\\hello_world.txt
PAUSE
该函数checkFirefoxProcesses()
查找打开的firefox
进程。要运行该示例,您必须打开一个firefox
会话。该函数在 BAT 文件的帮助下helloWorldToText()
创建一个文本文件。ECHO
该示例不会创建声明为startupinfo = info
. 当我在没有它的情况下运行subprocess
of 函数时。helloWorldToText()
startupinfo = info
案例:checkFirefoxProcesses()
没有运行startupinfo = info
和运行helloWorldToText()
运行startupinfo = info
。