How to programmatically open gnome-pomodoro timer window


I’ve been enjoying streaming on Twitch for a few weeks while I work on my daily tasks. I have gained a bit of a productivity boost because of the accountability effect of being on camera in front of a small audience.

One of the important self-care items for me while I stream is to take regular stretch breaks. I use gnome-pomodoro to give me regular reminders that it’s time for a break.

I’ve been playing around with Open Broadcaster Software Studio Automatic Scene Switcher and I though it would be really cool to automatically switch to a break scene whenever my Pomodoro work timer elapses.

gnome-pomodoro has a really nice feature of being able to run any arbitrary script in response to timers elapsing, timers being skipped, paused, etc. I used this feature to run a bash script when a break period begins.

My initial thought was to call gnome-pomodoro from said bash script which would bring gnome-pomodoro’s GUI to the foreground. Having the GUI activated serves two purposes. Firstly, it gives me a very obvious reminder for me to step away from the computer for a bit. Secondly, it triggers OBS Automatic Scene Switcher to switch to my break scene.

Open Broadcaster Software Studio Automatic Scene Switcher

Bringing the timer window to the screen proved somewhat difficult to do, because gnome-pomodoro doesn’t offer any way of bringing up the timer window via the CLI. The default window isn’t the timer, it’s statistics.

gnome-pomodoro stats window
gnome-pomodoro stats window

I thought to myself, there must be a way to get the timer window to display, so I began searching. Firstly, I checked the command line help.

chris@pop-os:~$ gnome-pomodoro --help-all
Usage:
  gnome-pomodoro [OPTION…]

Help Options:
  -h, --help               Show help options
  --help-all               Show all help options
  --help-gtk               Show GTK+ Options

GTK+ Options
  --class=CLASS            Program class as used by the window manager
  --name=NAME              Program name as used by the window manager
  --gdk-debug=FLAGS        GDK debugging flags to set
  --gdk-no-debug=FLAGS     GDK debugging flags to unset
  --gtk-module=MODULES     Load additional GTK+ modules
  --g-fatal-warnings       Make all warnings fatal
  --gtk-debug=FLAGS        GTK+ debugging flags to set
  --gtk-no-debug=FLAGS     GTK+ debugging flags to unset

Application Options:
  --start-stop             Start/Stop
  --start                  Start
  --stop                   Stop
  --pause-resume           Pause/Resume
  --pause                  Pause
  --resume                 Resume
  --no-default-window      Run as background service
  --preferences            Show preferences
  --quit                   Quit application
  --version                Print version information and exit
  --display=DISPLAY        X display to use

I didn’t see any way to default to the timer window in these options. I also checked man gnome-pomodoro and came to the conclusion that the only two windows directly callable via the CLI were the preferences window and the stats window.

I’m no stranger to GUI automation. I’m pretty comfortable with wmctrl and xdotool, utility programs for automating key presses, mouse clicks, moving windows around the desktop, and more.

I figured I would open gnome-pomodoro’s window first, followed by an xdotool incantation to click the button which displays the timer. Here’s the code I came up with for that.

#!/bin/bash

# /home/chris/.local/bin/pomodoro-to-top

# get the desktop we are on
DESKTOP=$(xdotool get_desktop)

# find pomo windows
WIDS=($(xdotool search --desktop $DESKTOP --class "gnome.pomodoro"))

# for each pomo window found
for WID in "${WIDS[@]}"
do

  # activate pomodoro window
  xdotool windowfocus --sync $WID

  sleep 0.25

  # Use F10 to get to default menu
  # Then Space to press the Timer button
  xdotool key --window $WID F10 KP_Space

done

This script worked okay, but there were certain scenarios where the pomodoro window wouldn’t get focus, and the following F10 and Space button presses would be sent to the wrong window.

“There must be a better way!” I thought.

I dug through the source code of gnome-pomodoro, determined to see if I could reverse engineer how the program opens it’s own window. If there was some sort of system call that I could mimick, that would be perfect.

The best thing I could find was that gnome-pomodoro’s activate_timer function calls this.show_window(“timer”) when I click the Timer option in it’s dropdown menu.

Unfortunately, I don’t have access to the same this object in memory that is used in gnome-pomodoro’s code. I’m sure there’s a way to get access to that, but I think going that route would involve hex code hacking and I don’t know much about that.

While browsing the code, I stumbled upon what looked like a manifest file. There were several mentions of dconf which gave me an idea. Dconf is a subsystem on linux which provides a way for processes to store configuration in a standardized way.

I poked around with gsettings for a few minutes, using gsettings list-schemas | grep -i pomodoro to find relevant configuration keys, and gsettings monitor to watch for changes as I toggled switches and edited values via gnome-pomodoro’s preferences. I didn’t see any way to trigger the window to open this way.

While I was learning about dconf, I stumbled upon d-bus, another subsystem in linux which provides a way for processes to communicate with other processes. I thought to myself, could there be a way to use d-bus to open the timer window in gnome-pomodoro?

I did a quick read about dbus and felt pretty confident that I would find a solution along this route. The article I read introduced me to a GUI program which is all about displaying all the available connections that can be made on my system using dbus, along with their methods.

On Pop!_OS 20.04, the packages I had to install to get QDBusViewer were qdbus-qt5 and qttools5-dev-tools

A qdbusviewer window displaying a filtered Session Bus services list, and a Methods list showing various org.gnome.Pomodoro d-bus methods.
qdbusviewer

I hit the jackpot after installing qdbusviewer and searching for “pomodoro”. I browsed through the tree of methods and there it was. org.gnome.Pomodoro.ShowMainWindow !

Right clicking on that method in gdbusviewer, I found that I could call the ShowMainWindow method with parameters mode and timestamp. For mode, I entered “timer”, and I left timestamp at it’s default value 0.

It worked! Calling org.gnome.Pomodoro.ShowMainWindow via QDBusViewer resulted in the Timer window appearing on my screen.

Now all that was left was finding a way to call the same d-bus method via the command line, so I could invoke the method via the bash script which gets called by gnome-pomodoro. Here’s what I came up with, using dbus-send.

dbus-send --session --dest=org.gnome.Pomodoro --type=method_call /org/gnome/Pomodoro org.gnome.Pomodoro.ShowMainWindow string:"timer" uint32:0

Great success! Now when it’s break time, I get a large timer window on my screen which OBS Automatic Scene Switcher can detect. Look ma, no hands! I can simply walk away from the computer while my camera scene is automatically switched off.

Thanks so much for reading my article. What did you think? Let me know in the comments below.

Looking for VOCALOID trading cards?

Check out Sakura Blossom Trading Post

Looking for VOCALOID trading cards?

Check out Sakura Blossom Trading Post