2

I tried the example in a Raspberry Pi SE question, creating a systemd ".service" in the past and it worked flawlessly, but now I'm running Tkinter with python3 on a raspberry pi3.

[Unit] Description=GUI Start
After=graphical.target
Wants=graphical.target

[Service]
User=pi
Group=pi
ExecStart=/bin/bash -c "export DISPLAY=:0; export XAUTHORITY=/home/pi/.Xauthority; /usr/bin/python3 /home/pi/ampolas/ampolas.py"

[Install]
WantedBy=graphical.target

but I now get a display:0 error like:

_tkinter.TclError: couldn't connect to display :0.0

when I run echo $DISPLAY I get DISPLAY:0.0. But it seems that on bootup it's not recognized

When I run sudo systemctl daemon-reload,
then ...enable
then ... start
it runs okay, but even After=grafical.target, it seems DISPLAY:0 isn't defined yet

I'm not familiar enough with Linux to understand what's going on under the hood.

4
  • 2
    You can't start GUI programs with a service file. Use the autostart function of LXDE (search for that on here).
    – Dougie
    Commented Sep 18, 2020 at 20:23
  • hey Dougie thanks for the relpy, I did manage to get it to work on another fresh install of the raspiOS. But are you suggesting its not a good way to do it? Is there a safer way? This is running a HMI on an industrial machine,I'm worried that it could fail in future. Commented Sep 19, 2020 at 0:08
  • It's not a good way. The services are started before the GUI starts.
    – Dougie
    Commented Sep 19, 2020 at 0:17
  • @Dougie Qoute: "You can't start GUI programs with a service file" - sorry, but that is not true.
    – Ingo
    Commented Sep 19, 2020 at 8:27

3 Answers 3

2

You wrote:

when I run echo $DISPLAY I get DISPLAY:0.0

This is wrong. You must only get the environment value:

rpi ~$ export DISPLAY=:0.0
rpi ~$ echo $DISPLAY
:0.0

rpi ~$ export DISPLAY=DISPLAY:0.0   # WRONG!
rpi ~$ echo $DISPLAY
DISPLAY:0.0

Please correct this. Then you should define an environment for the service, not only for the shell script. Try this:

[Unit]
Description=GUI Start
After=graphical.target
Wants=graphical.target

[Service]
User=pi
Group=pi
Environment="DISPLAY=:0.0"
Environment="XAUTHORITY=/home/pi/.Xauthority"
#ExecStartPre=/usr/bin/printenv
ExecStart=/usr/bin/python3 /home/pi/ampolas/ampolas.py

[Install]
WantedBy=graphical.target

If this also does not work, then uncomment the #ExecStartPre=/usr/bin/printenv to show what environment is given at runtime and what's wrong with it. Reboot and you will find the output with:

rpi ~$ journalctl -b
1
  1. Okay so I got it to work, and it turns out, and I dont know why; adding this line :
# Disable bluetooth
dtoverlay=pi3-disable-bt

to my config.txt file is what caused the error.

I copied that example from this post :

http://himeshp.blogspot.com/2018/08/fast-boot-with-raspberry-pi.html

and it was what caused the display error. No clue as to why, but I would love to know.

2
  • And what is the solution? Removing dtoverlay=pi3-disable-bt from /boot/config.txt?
    – Ingo
    Commented Sep 21, 2020 at 9:35
  • Please mark the answer as the accepted one with a click on the tick on its left side. That prevents your Question from being shown as a unsolved Post to the community and saves them/us a lot of work.
    – Ingo
    Commented Sep 21, 2020 at 19:58
0

I spent 5 hours getting this working just now after trying all of these other solutions under the sun, so let me finally put this to rest.

Note: This is for raspbian, with main user account using the default username ("pi")

Here are the steps in order:


Name your python file main.py and drag your python file to the desktop.


Next, create a new plain text file and add the following contents:

#!/bin/bash

python3 /home/pi/Desktop/main.py

Save this text file as launch.command on the desktop. This is shell script to launch your python file. By default it won't work, we have to chmod it (next step)


Run terminal and run the following command:

chmod u+x /home/pi/Desktop/launch.command

Now double clicking launch.command (and selecting execute) will launch your python file.


At this point, we are ready to get it launching on boot. If you've done any other launch attempts prior to this please undo all of those file changes you had done.


Open terminal and run the following:

sudo nano /etc/systemd/system/myproject.service

We are just going to call it myproject for now, don't change any of this until after you get it working, then feel free to attempt a rename


In the window that pops up, copy paste the following exactly:

[Unit]
Description=Start Myproject
After=graphical.target
Wants=graphical.target

[Service]
User=pi
Group=pi
ExecStart=/bin/bash -c "export DISPLAY=:0; export XAUTHORITY=/home/pi/.Xauthority; /home/pi/Desktop/launch.command"

[Install]
WantedBy=graphical.target

Now press ctrl+x to exit-and-save, it will prompt you to save changes, type "y", the filename should already be entered as .../myproject.service, if it is then press enter and it will save and exit, if the file name is blank it messed up (this just happens sometimes), quit terminal and try all of this again, sorry.


Now in terminal enter:

sudo systemctl daemon-reload

Then

sudo systemctl enable myproject.service

Lastly

sudo reboot


On launch, before anything else shows (after the boot up splash screen shows of course, but before desktop shows) your GUI will now launch, congrats!

I recommend you launch it full screen, to do that edit your python file to use this:

root.attributes('-fullscreen', True)

NOTE, 'root' is likely not what you called your TK() init.... at the end of your code you have something like XXXX.mainloop(), change 'root' to whatever XXXX is, stick this right after your init of TK()


Once you've reboot, you are likely stuck in the app (especially if you launched it full screen), things like alt+f4 or alt+f11 won't kill your program. To exit, press the windows/menu button on your keyboard, the access panel will appear you and can go to accessories>terminal to launch a new terminal window, then run the following:

sudo systemctl stop myproject.service

The program will be killed and you will be back to your standard desktop...

NOW, to prevent it from launching again on bootup, simply rename your launch.command file to DISABLED_launch.command and when you're ready to start launching on bootup again set the name back.


Go get a drink, you've earned it.

Also, you can obviously put these places other than desktop but MAKE SURE you always use the full path in any of these commands, don't use the '~/..' shortcut.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.