python - PyQt4 Minimizar a la bandeja
system-tray minimize (7)
¿Hay una manera de minimizar a la bandeja en PyQt4? Ya he trabajado con la clase QSystemTrayIcon, pero ahora me gustaría minimizar u "ocultar" la ventana de mi aplicación y mostrar solo el icono de la bandeja.
¿Alguien ha hecho esto? Cualquier dirección podría ser apreciada.
Uso de Python 2.5.4 y PyQt4 en Windows XP Pro
Aquí está el código de trabajo ... Gracias a Matze por Crucial , la SEÑAL me llevó más horas de curiosidad ... pero haciendo otras cosas. así que para un #! momento :-)
def create_sys_tray(self):
self.sysTray = QtGui.QSystemTrayIcon(self)
self.sysTray.setIcon( QtGui.QIcon(''../images/corp/blip_32.png'') )
self.sysTray.setVisible(True)
self.connect(self.sysTray, QtCore.SIGNAL("activated(QSystemTrayIcon::ActivationReason)"), self.on_sys_tray_activated)
self.sysTrayMenu = QtGui.QMenu(self)
act = self.sysTrayMenu.addAction("FOO")
def on_sys_tray_activated(self, reason):
print "reason-=" , reason
El código ayuda, así que aquí hay algo que escribí para una aplicación, excepto el evento closeEvent en lugar del evento minim.
Notas:
"closeEvent (evento)" es un evento Qt invalidado, por lo que debe incluirse en la clase que implementa la ventana que desea ocultar.
"okayToClose ()" es una función que podría considerar implementar (o una bandera booleana que tal vez quiera almacenar) ya que a veces realmente desea salir de la aplicación en lugar de minimizarla a systray.
También hay un ejemplo de cómo mostrar () su ventana nuevamente.
def __init__(self):
traySignal = "activated(QSystemTrayIcon::ActivationReason)"
QtCore.QObject.connect(self.trayIcon, QtCore.SIGNAL(traySignal), self.__icon_activated)
def closeEvent(self, event):
if self.okayToClose():
#user asked for exit
self.trayIcon.hide()
event.accept()
else:
#"minimize"
self.hide()
self.trayIcon.show() #thanks @mojo
event.ignore()
def __icon_activated(self, reason):
if reason == QtGui.QSystemTrayIcon.DoubleClick:
self.show()
Es bastante sencillo una vez que recuerdas que no hay forma de minimizarlo en la bandeja del sistema .
En su lugar, lo finges haciendo esto:
- Captura el evento minimizado en tu ventana
- En el controlador de eventos de minimización, cree y muestre un QSystemTrayIcon
- También en el controlador de eventos de minimización, llame a hide () o setVisible (false) en su ventana
- Capture un clic / doble clic / elemento de menú en el icono de la bandeja del sistema
- En el controlador de eventos del icono de la bandeja del sistema, llame a show () o setVisible (verdadero) en su ventana, y opcionalmente oculte el icono de la bandeja.
Esta es la forma correcta de manejar el doble clic en el icono de una bandeja para PyQt5.
def _create_tray(self):
self.tray_icon = QSystemTrayIcon(self)
self.tray_icon.activated.connect(self.__icon_activated)
def __icon_activated(self, reason):
if reason in (QSystemTrayIcon.Trigger, QSystemTrayIcon.DoubleClick):
pass
Esta fue una edición de la respuesta de vzades, pero fue rechazada por varios motivos. Hace exactamente lo mismo que su código pero también obedece el evento de minimización (y se ejecuta sin errores de sintaxis / íconos que faltan)
import sys
from PyQt4 import QtGui, QtCore
class Example(QtGui.QWidget):
def __init__(self):
super(Example, self).__init__()
self.initUI()
def initUI(self):
style = self.style()
# Set the window and tray icon to something
icon = style.standardIcon(QtGui.QStyle.SP_MediaSeekForward)
self.tray_icon = QtGui.QSystemTrayIcon()
self.tray_icon.setIcon(QtGui.QIcon(icon))
self.setWindowIcon(QtGui.QIcon(icon))
# Restore the window when the tray icon is double clicked.
self.tray_icon.activated.connect(self.restore_window)
def event(self, event):
if (event.type() == QtCore.QEvent.WindowStateChange and
self.isMinimized()):
# The window is already minimized at this point. AFAIK,
# there is no hook stop a minimize event. Instead,
# removing the Qt.Tool flag should remove the window
# from the taskbar.
self.setWindowFlags(self.windowFlags() & ~QtCore.Qt.Tool)
self.tray_icon.show()
return True
else:
return super(Example, self).event(event)
def closeEvent(self, event):
reply = QtGui.QMessageBox.question(
self,
''Message'',"Are you sure to quit?",
QtGui.QMessageBox.Yes | QtGui.QMessageBox.No,
QtGui.QMessageBox.No)
if reply == QtGui.QMessageBox.Yes:
event.accept()
else:
self.tray_icon.show()
self.hide()
event.ignore()
def restore_window(self, reason):
if reason == QtGui.QSystemTrayIcon.DoubleClick:
self.tray_icon.hide()
# self.showNormal will restore the window even if it was
# minimized.
self.showNormal()
def main():
app = QtGui.QApplication(sys.argv)
ex = Example()
ex.show()
sys.exit(app.exec_())
if __name__ == ''__main__'':
main()
Este es el código y ayuda, creo en mostrarme el código
import sys
from PyQt4 import QtGui, QtCore
from PyQt4.QtGui import QDialog, QApplication, QPushButton, QLineEdit, QFormLayout, QSystemTrayIcon
class Example(QtGui.QWidget):
def __init__(self):
super(Example, self).__init__()
self.initUI()
def initUI(self):
self.icon = QSystemTrayIcon()
r = self.icon.isSystemTrayAvailable()
print r
self.icon.setIcon(QtGui.QIcon(''/home/vzades/Desktop/web.png''))
self.icon.show()
# self.icon.setVisible(True)
self.setGeometry(300, 300, 250, 150)
self.setWindowIcon(QtGui.QIcon(''/home/vzades/Desktop/web.png''))
self.setWindowTitle(''Message box'')
self.show()
self.icon.activated.connect(self.activate)
self.show()
def closeEvent(self, event):
reply = QtGui.QMessageBox.question(self, ''Message'', "Are you sure to quit?", QtGui.QMessageBox.Yes |
QtGui.QMessageBox.No, QtGui.QMessageBox.No)
if reply == QtGui.QMessageBox.Yes:
event.accept()
else:
self.icon.show()
self.hide()
event.ignore()
def activate(self, reason):
print reason
if reason == 2:
self.show()
def __icon_activated(self, reason):
if reason == QtGui.QSystemTrayIcon.DoubleClick:
self.show()
def main():
app = QtGui.QApplication(sys.argv)
ex = Example()
sys.exit(app.exec_())
if __name__ == ''__main__'':
main()
Solo para agregar al ejemplo de Chris:
Es crucial que use la notación Qt al declarar la señal, es decir,
correcto :
self.connect(self.icon, SIGNAL("activated(QSystemTrayIcon::ActivationReason)"), self.iconClicked)
y no el de PyQt
incorrecto y no funcionará:
self.connect(self.icon, SIGNAL("activated(QSystemTrayIcon.ActivationReason)"), self.iconClicked)
Tenga en cuenta la ::
en la cadena de señal. Esto me tomó cerca de tres horas para averiguarlo.