Difference between revisions of "Linux - Screen Control"

From Da Nerd Mage Wiki
Jump to navigation Jump to search
 
(14 intermediate revisions by the same user not shown)
Line 8: Line 8:


Specifically set up for all-in-one machines & laptops since these are a little difficult to shut off the screen without shutting down the machine itself.
Specifically set up for all-in-one machines & laptops since these are a little difficult to shut off the screen without shutting down the machine itself.
== The Script ==
* <code>sudo apt install vbetool</code>
* <code>sudo apt install vbetool</code>


== The Script ==
The following script needs to run as root...
The following script needs to run as root...


* <code>sudo vi /usr/local/bin/screenremote.py</code>  
* <code>sudo vi /usr/local/bin/screenremote.py</code>  
#!/usr/bin/env python
 
<syntaxhighlight lang="python" line>
import paho.mqtt.client as mqttClient
#!/usr/bin/env python
import time
 
import os
import paho.mqtt.client as mqttClient
import subprocess
import time
import socket
import os
import subprocess
###################################################################################################
import socket
 
hostname = socket.gethostname()
###################################################################################################
broker_address = "skynet"
 
port = 1883
hostname = socket.gethostname()
topic = hostname + "/#"
broker_address = "skynet"
user = "user"
port = 1883
password = "password"
topic = hostname + "/#"
client = mqttClient.Client(hostname + "control")
user = "user"
client.username_pw_set(user, password=password)
password = "password"
client = mqttClient.Client(hostname + "control")
###################################################################################################
client.username_pw_set(user, password=password)
##    Broker Connection    ##
 
###################################################################################################
###################################################################################################
##    Broker Connection    ##
Connected = False
###################################################################################################
 
def on_connect(client, userdata, flags, rc):
Connected = False
    global Connected
 
    if rc == 0:
def on_connect(client, userdata, flags, rc):
        print("          HostName: ", hostname)
    global Connected
        print("Connected to broker: ", broker_address)
    if rc == 0:
        print("      Subscribed to: ", topic)
        print("          HostName: ", hostname)
        print()
        print("Connected to broker: ", broker_address)
        Connected =True
        print("      Subscribed to: ", topic)
    else:
        print()
        print("Connection failed")
        Connected =True
        Connected =False
    else:
        print("Connection failed")
###################################################################################################
        Connected =False
##    Message Handling    ##
 
###################################################################################################
###################################################################################################
##    Message Handling    ##
def on_message(client, userdata, message):
###################################################################################################
    print( " Received message: " + str(message.payload.decode("utf-8")))
 
    print( "        on topic: " + message.topic)
def on_message(client, userdata, message):
    #print( "        with QoS: " + str(message.qos))
    print( " Received message: " + str(message.payload.decode("utf-8")))
    print( "        on topic: " + message.topic)
    time.sleep(1)
    #print( "        with QoS: " + str(message.qos))
 
### Display control (turn the screen on or off...)
    time.sleep(1)
    if message.topic == hostname + "/display":
 
        command = "/usr/sbin/vbetool dpms " + str(message.payload.decode("utf-8"))
### Display control (turn the screen on or off...)
        print( command )
    if message.topic == hostname + "/display":
        os.system(command)
        command = "/usr/sbin/vbetool dpms " + str(message.payload.decode("utf-8"))
### Audio control (something for th future...)
        print( command )
    elif message.topic == hostname + "/audio":
        os.system(command)
        print("audio stuff")
### Audio control (something for th future...)
### Not any sort of valid topic...
    elif message.topic == hostname + "/audio":
    else:
        print("audio stuff")
        print("Not Important to us...")
### Not any sort of valid topic...
    else:
    print()
        print("Not Important to us...")
 
###################################################################################################
    print()
 
client.on_connect = on_connect
###################################################################################################
client.on_message = on_message
 
client.on_connect = on_connect
client.connect(broker_address, port=port)
client.on_message = on_message
client.loop_start()
 
client.connect(broker_address, port=port)
while Connected != True:
client.loop_start()
    time.sleep(0.1)
 
while Connected != True:
client.subscribe(topic)
    time.sleep(0.1)
 
try:
client.subscribe(topic)
    while True:
 
        time.sleep(1)
try:
    while True:
except KeyboardInterrupt:
        time.sleep(1)
    print( "exiting" )
 
    client.disconnect()
except KeyboardInterrupt:
    client.loop_stop()
    print( "exiting" )
    client.disconnect()
    client.loop_stop()
 
 
</syntaxhighlight>
 
* <code>sudo chmod +x /usr/local/bin/screenremote.py</code>
* <code>sudo chmod +x /usr/local/bin/screenremote.py</code>
This will respond to MQTT messages:
This will respond to MQTT messages:
Line 107: Line 114:


* <code>sudo vi /etc/systemd/system/remote-screen-control.service</code>
* <code>sudo vi /etc/systemd/system/remote-screen-control.service</code>
[Unit]
 
Description=Watch for MQTT messages to turn screen on/off
<syntaxhighlight lang="ini" line>
After=multi-user.target
[Unit]
Description=Watch for MQTT messages to turn screen on/off
[Service]
Documentation=https://wiki.nerdmage.ca/index.php/Linux_-_Screen_Control
ExecStart=<code>/usr/local/bin/screenremote.py</code>
After=multi-user.target network.target
Type=simple
 
[Service]
[Install]
ExecStart=<code>/usr/local/bin/screenremote.py</code>
WantedBy=multi-user.target
Type=simple
Restart=on-failure
 
[Install]
WantedBy=multi-user.target
</syntaxhighlight>
 
* <code>sudo systemctl daemon-reload</code>
 
 
* <code>sudo systemctl enable remote-screen-control.service</code>
* <code>sudo systemctl enable remote-screen-control.service</code>
* <code>sudo systemctl start remote-screen-control.service</code>
* <code>sudo systemctl start remote-screen-control.service</code>
Line 122: Line 138:


== Notes ==
== Notes ==
For some older systems, '''vbetool''' fails.
=== non vbetool capable systems ===
For some systems, '''vbetool''' fails.


In this case, if the system has '''X''' installed (i.e.: it has a GUI), '''xset''' might do the job in its place.
In this case, if the system has '''X''' installed (i.e.: it has a GUI), '''xset''' might do the job in its place.
Line 128: Line 145:
* <code>xset -display :0.0 dpms force off</code>
* <code>xset -display :0.0 dpms force off</code>
* <code>xset -display :0.0 dpms force on</code>
* <code>xset -display :0.0 dpms force on</code>
<span style="color: rgb(186, 55, 42);" >As of yet... No solution for systems without '''X'''.</span>
=== Python Weirdness ===
Sometimes, '''Python''' & it's tools & modules are a little problematic.
Installing '''Python3''' & '''paho-mqtt''' directly will force this to work. (&, of course, you should force it to be '''Python3'''...)
* <code>sudo apt install python-is-python3 python3-paho-mqtt</code>
=== Broker temporarily offline causes failure ===
If this service loses contact with the broker, it does not try to find it again.  Must find a solution to this...
Meanwhile:
* <code>sudo systemctl restart remote-screen-control.service</code>
gets it back online.

Latest revision as of 11:55, 11 October 2024

Proven on:
Logo Debian.png
12 (bookworm)

This little setup allows for remote control (via MQTT) of the screen(s) of Linux-based computers.

Specifically set up for all-in-one machines & laptops since these are a little difficult to shut off the screen without shutting down the machine itself.

The Script

  • sudo apt install vbetool

The following script needs to run as root...

  • sudo vi /usr/local/bin/screenremote.py
#!/usr/bin/env python

import paho.mqtt.client as mqttClient
import time
import os
import subprocess
import socket

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

hostname = socket.gethostname()
broker_address = "skynet"
port = 1883
topic = hostname + "/#"
user = "user"
password = "password"
client = mqttClient.Client(hostname + "control")
client.username_pw_set(user, password=password)

###################################################################################################
##    Broker Connection    ##
###################################################################################################

Connected = False

def on_connect(client, userdata, flags, rc):
    global Connected
    if rc == 0:
        print("           HostName: ", hostname)
        print("Connected to broker: ", broker_address)
        print("      Subscribed to: ", topic)
        print()
        Connected =True
    else:
        print("Connection failed")
        Connected =False

###################################################################################################
##    Message Handling    ##
###################################################################################################

def on_message(client, userdata, message):
    print( " Received message: " + str(message.payload.decode("utf-8")))
    print( "         on topic: " + message.topic)
    #print( "         with QoS: " + str(message.qos))

    time.sleep(1)

### Display control (turn the screen on or off...)
    if message.topic == hostname + "/display":
        command = "/usr/sbin/vbetool dpms " + str(message.payload.decode("utf-8"))
        print( command )
        os.system(command)
### Audio control (something for th future...)
    elif message.topic == hostname + "/audio":
        print("audio stuff")
### Not any sort of valid topic...
    else:
        print("Not Important to us...")

    print()

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

client.on_connect = on_connect
client.on_message = on_message

client.connect(broker_address, port=port)
client.loop_start()

while Connected != True:
    time.sleep(0.1)

client.subscribe(topic)

try:
    while True:
        time.sleep(1)

except KeyboardInterrupt:
    print( "exiting" )
    client.disconnect()
    client.loop_stop()
  • sudo chmod +x /usr/local/bin/screenremote.py

This will respond to MQTT messages:

  • HOSTNAME/display on
  • HOSTNAME/display off

The Service

It works as a systemd service

  • sudo vi /etc/systemd/system/remote-screen-control.service
[Unit]
Description=Watch for MQTT messages to turn screen on/off
Documentation=https://wiki.nerdmage.ca/index.php/Linux_-_Screen_Control
After=multi-user.target network.target

[Service]
ExecStart=<code>/usr/local/bin/screenremote.py</code>
Type=simple
Restart=on-failure

[Install]
WantedBy=multi-user.target
  • sudo systemctl daemon-reload


  • sudo systemctl enable remote-screen-control.service
  • sudo systemctl start remote-screen-control.service
  • sudo systemctl status remote-screen-control.service

Notes

non vbetool capable systems

For some systems, vbetool fails.

In this case, if the system has X installed (i.e.: it has a GUI), xset might do the job in its place.

  • xset -display :0.0 dpms force off
  • xset -display :0.0 dpms force on

As of yet... No solution for systems without X.

Python Weirdness

Sometimes, Python & it's tools & modules are a little problematic.

Installing Python3 & paho-mqtt directly will force this to work. (&, of course, you should force it to be Python3...)

  • sudo apt install python-is-python3 python3-paho-mqtt

Broker temporarily offline causes failure

If this service loses contact with the broker, it does not try to find it again. Must find a solution to this...

Meanwhile:

  • sudo systemctl restart remote-screen-control.service

gets it back online.