Auto Open Separate Windows of Chromium on Raspbian

I was recently tasked with creating a digital menu for a local company. We went through several options and settled on running dual 4k monitors with a Raspberry Pi 4 displaying a menu made in Google Sheets. Sounds pretty straight forward, and it was, until it came to automatically opening two chromium instances to separate web pages and on different displays.

Auto starting one or more instances of chrome is a snap, just add the following to /etc/xdg/lxsession/LXDE-pi/autostart:

@/usr/bin/chromium-browser --new-window --kiosk --disable-restore-session-state http://exampleemailaddress.com

But to make two separate windows and have one auto open on each monitor you’ll need to add the following to the end of the command listed above in /etc/xdg/lxsession/LXDE-pi/autostart:

-user-data-dir=default0 --window-position=0,0

and for the second monitor / session you’ll add another @/usr/bin/chromium-browser --new-window --kiosk --disable-restore-session-state http://exampleemailaddress.com -user-data-dir=default0 --window-position=0,0 to /etc/xdg/lxsession/LXDE-pi/autostart changing the last two flags to: -user-data-dir=default1 --window-position=1080,0 (note that this is for a pair of vertically mounted 1080P displays, your value may vary).

Your final /etc/xdg/lxsession/LXDE-pi/autostart will have the following two lines at the bottom:

@/usr/bin/chromium-browser –new-window –kiosk –disable-restore-session-state http://exampleemailaddress.com -user-data-dir=default0 –window-position=0,0

@/usr/bin/chromium-browser –new-window –kiosk –disable-restore-session-state http://exampleemailaddress.com -user-data-dir=default0 –window-position=1080,0

Lastly you can add the unclutter application to hide the mouse cursor. To add unclutter just open an command prompt and run: sudo apt-get install unclutter then add @unlutter to your /etc/xdg/lxsession/LXDE-pi/autostart file.

Update 2/9/2020:

The menu system has been working fairly well with two exceptions. Updating the menus required using VNC to connect to the raspberry pi, exit presentation mode on both displays, and then re-enter presentation mode. Additionally after reboot the menu’s required manual intervention to be placed into presentation mode. I solved this issue using xdotool, installed by running sudo apt-get install xdotool. This allows me to script keyboard presses so after boot a script presses ctrl+shift+F5 and alt+Escape to enter presentation mode on the selected chrome / google slides instance, then switch to the other instance to repeat.

I solved the refresh issue by slapping together a quick and dirty Python / Flask app that allows users to call the script to exit presentation mode one each chrome instance which will allow slides to grab any changes made to the slides, then after a short delay reenter presentation mode. I also added an option to reboot the Pi’s via the web ui. Here is the Python:

from flask import Flask, render_template, request
import subprocess

app = Flask(__name__)


@app.route('/', methods=['GET', 'POST'])
def index():
    if request.form.get('refresh_button') == 'refresh menu':
        print('resfresh')  # do something
        cmd = ["/somepath/refresh_script.sh"]
        p = subprocess.Popen(cmd, stdout=subprocess.PIPE,
                             stderr=subprocess.PIPE,
                             stdin=subprocess.PIPE)
        out = p.communicate()
        print(out)
    else:
        print('reboot')  # do something else
        cmd = ["/somepath/reboot_script.sh"]
        p = subprocess.Popen(cmd, stdout=subprocess.PIPE,
                             stderr=subprocess.PIPE,
                             stdin=subprocess.PIPE)
        out1 = p.communicate()
        print(out1)
    return render_template('index.html')


if __name__ == '__main__':
    app.run()

and index.html:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Menu Control</title>
</head>
<body>
<form method="post" action="/">
    <p style="text-align: center;font-size:30px">Menu Controller</p>
<div style="text-align: center; border: 1px solid">
    <p>Press Refresh Menu to update the displays. Use this option after updating menus in google slides.</p>
    <p><input type = "submit" name = "refresh_button" class="btn btn-outline-primary" value = "refresh menu" style="height:75px;width:200px;background-color:green;color:black;font-size:30px"/></p>
</div>
    <div style="text-align: center; border: 1px solid">
        <p>Press Reboot to reboot the menus, this will take several minutes to complete. Only use this if the menus are not functioning correctly</p>
<p><input type = "submit" name = "restart_button" class="btn btn-outline-primary" style="background-color:red;color:black" value = "restart menu"  /></p>
    </div>
</form>
</body>
</html>

Its not pretty but its functional and much easier than doing it manually. and finally the bit of bash called to refresh the menu / enter presentation mode on boot:

#!/bin/bash
sleep 30
xdotool key ctrl+shift+F5
sleep 30
xdotool key alt+Escape
sleep 30
xdotool key ctrl+shift+F5