-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathshutdownTimer.py
More file actions
157 lines (120 loc) · 4.56 KB
/
Copy pathshutdownTimer.py
File metadata and controls
157 lines (120 loc) · 4.56 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
#!/usr/bin/env python3
import sys
import os
import time
from PyQt5 import QtWidgets, QtGui, QtCore
from PyQt5.QtNetwork import QLocalServer, QLocalSocket
class ShutdownTimer(QtWidgets.QSystemTrayIcon):
def __init__(self):
super().__init__()
self.duration = 60*60 # seconds (1 hour)
self.interval = 1 # update every second
self.elapsed = 0
self.setToolTip("Shutdown Timer")
self.menu = QtWidgets.QMenu()
restart_action = self.menu.addAction("Restart Timer")
restart_action.triggered.connect(self.restart_timer)
cancel_action = self.menu.addAction("Cancel Shutdown")
cancel_action.triggered.connect(self.cancel_shutdown)
self.setContextMenu(self.menu)
self.activated.connect(self.on_tray_icon_clicked)
self.update_icon()
self.show()
self.start_timers()
def start_timers(self):
self.timer = QtCore.QTimer()
self.timer.timeout.connect(self.update_timer)
self.timer.start(self.interval * 1000)
self.shutdown_timer = QtCore.QTimer()
self.shutdown_timer.setSingleShot(True)
self.shutdown_timer.timeout.connect(self.shutdown)
self.shutdown_timer.start(self.duration * 1000)
def restart_timer(self):
self.elapsed = 0
self.setToolTip("Shutdown Timer")
self.update_icon()
self.timer.stop()
self.shutdown_timer.stop()
self.start_timers()
def on_tray_icon_clicked(self, reason):
if reason == QtWidgets.QSystemTrayIcon.Trigger: # Left-click
self.restart_timer()
def update_timer(self):
self.elapsed += self.interval
remaining = max(0, self.duration - self.elapsed)
minutes_left = remaining // 60
if remaining < 60:
self.setToolTip(f"Shutdown Timer - {remaining} sec remaining")
else:
self.setToolTip(f"Shutdown Timer - {minutes_left} min remaining")
self.update_icon()
def update_icon(self):
progress = min(1.0, self.elapsed / self.duration)
pixmap = QtGui.QPixmap(64, 64)
pixmap.fill(QtCore.Qt.transparent)
painter = QtGui.QPainter(pixmap)
painter.setRenderHint(QtGui.QPainter.Antialiasing)
rect = QtCore.QRectF(0, 0, 64, 64)
# Draw full green circle
painter.setBrush(QtGui.QColor(0, 255, 0))
painter.setPen(QtCore.Qt.NoPen)
painter.drawEllipse(rect)
# Draw red arc covering elapsed part
if progress > 0:
painter.setBrush(QtGui.QColor(255, 0, 0))
painter.setPen(QtCore.Qt.NoPen)
path = QtGui.QPainterPath()
path.moveTo(rect.center())
path.arcTo(rect, 90, -360 * progress)
path.lineTo(rect.center())
painter.drawPath(path)
painter.end()
self.setIcon(QtGui.QIcon(pixmap))
def shutdown(self):
os.system("wmctrl -c 'Firefox'")
time.sleep(1)
os.system("systemctl poweroff")
def cancel_shutdown(self):
self.shutdown_timer.stop()
self.timer.stop()
exit()
class SingleInstance:
def __init__(self, name, on_message):
self.name = name
self.on_message = on_message
self.server = QLocalServer()
if self.server.listen(self.name):
# This is the first instance
self.server.newConnection.connect(self.handle_connection)
self.is_primary = True
else:
# Connect to the first instance and send message
self.is_primary = False
self.send_message("RESTART")
def handle_connection(self):
socket = self.server.nextPendingConnection()
socket.readyRead.connect(lambda: self.read_message(socket))
def read_message(self, socket):
msg = bytes(socket.readAll()).decode()
if msg == "RESTART":
self.on_message()
def send_message(self, message):
socket = QLocalSocket()
socket.connectToServer(self.name)
if socket.waitForConnected(1000):
socket.write(message.encode())
socket.flush()
socket.waitForBytesWritten(1000)
socket.close()
def main():
app = QtWidgets.QApplication(sys.argv)
app.setQuitOnLastWindowClosed(False)
tray = ShutdownTimer()
# Create unique instance handler
instance = SingleInstance("shutdown-timer-instance", tray.restart_timer)
if not instance.is_primary:
# This is a second instance, exit silently
sys.exit(0)
sys.exit(app.exec_())
if __name__ == "__main__":
main()