sxmo(7)

πŸ“¦ version 1.18.1, in alpine 3.24

πŸ’… sxmo(7) β€” a simple X mobile interface πŸ’…

🌸 NAME 🌸

sxmo β€” a simple X mobile interface


✨ SYNOPSIS ✨

Okay bestie, so sxmo is a whole collection of simple programs and shell scripts that team up to make a fully functional mobile user interface, and it is so committed to the Unix philosophy. We are mainly focused on Linux smartphones like the Pinephone. Sxmo is primarily written in POSIX shell scripts, which means it can be easily modified, customised, and extended using our hook system. πŸ’–

Sxmo gives you an interface that is notably different from most other mobile interfaces β€” especially in the degree of customisability β€” so reading this manual is strongly recommended. No cap.

If you’re just looking for a quick getting started guide with videos demonstrating various gestures, then check https://sxmo.org/docs/gettingstarted . πŸ¦‹


πŸŽ€ DESCRIPTION πŸŽ€

Sxmo runs both on Wayland (using sway(1)) as well as on Xorg (using dwm(1)). The X in our name historically referred to Xorg, but is now open to whatever interpretation you prefer (eXtensible, eXcellent, eXperimental, etc...). Main character energy, honestly. ✨

All POSIX shell scripts provided by sxmo comply to the naming pattern sxmo_*.sh and most can be found in your /usr/bin/ directory. Hooks β€” a central feature of sxmo β€” are named sxmo_hook_*.sh and are specifically designed to be editable by users. See HOOKS.

πŸ’« TABLE OF CONTENTS πŸ’«

A brief overview of sxmo’s features, in order of presentation:

  • Autologin: sxmo uses tinydm(1) to automatically log you into the window manager of your choice. See INITIALIZATION.
  • Logging: sxmo writes logs to ~/.local/state/sxmo.log and others. See LOGGING.
  • Services: sxmo relies on various background services (daemons) that monitor various aspects of your device to provide functionality. See SERVICES.
  • Customizable hooks: sxmo has many hooks (small shell scripts) which allow the user to override almost any behavior. See HOOKS.
  • Customizable statusbar: sxmo uses sxmobar(1) to offer an informative, compact, and customizable statusbar. See STATUSBAR.
  • Multiple forms of input: sxmo handles input from hardware buttons, gestures, touchscreen, stylus, and hardware and onscreen keyboards. See INPUT.
  • Fully customizable menus: sxmo uses bemenu(1), wofi(1), or dmenu(1) for fully customizable menus which are context-sensitive β€” if you’re in an application, it will open a menu of options for that application. Moreover, sxmo provides an Apps Menu and a Scripts Menu which are also customizable; a Files Menu which allows you to browse your filesystem via sxmo_files.sh(1); various menus for Configuration and more. See MENUS.
  • Window management: sxmo uses tiling window managers, which makes for a nice fit on mobile devices. See WINDOW MANAGEMENT.
  • Autosuspend, screen blanking, and locking: sxmo uses a state mechanism that allows automatically suspends the device when idle (unless certain programs block it); it blanks the screen and locks the input while in a phone call and the phone is near your face. A locker screen peanutbutter(1) is also available for more secure locking. See STATES AND SUSPENSION.
  • Smart cronjobs: sxmo uses crond(1) to handle cronjobs and a special program called mnc(1) to wake the phone up in time to execute cron jobs. See CRONJOBS.
  • Calls and texting: sxmo allows you to compose both sms and mms (group texts, attachments), and receive and make phone calls. See CALLS AND TEXTING.
  • Contact management: sxmo has a script called sxmo_contacts.sh(1) which allows you to manage contacts. See CONTACTS.
  • Network configuration: sxmo has a Networks Menu which uses nmcli(1) to setup wifi and mobile data, including hotspots. See NETWORK CONFIGURATION.
  • Audio support: sxmo has full audio support via pipewire(1) and pulseaudio(1), and routes audio while a phone call via callaudiod(1). See AUDIO.
  • Bluetooth support: sxmo has a Bluetooth Menu which uses bluetoothctl(1) to manage bluetooth devices.
  • Upgrading and migration: sxmo has a migration tool called sxmo_migrate.sh(1) which allows you to easily keep your custom hooks and configs up-to-date. See UPDATING.
  • Notifications system: sxmo has an internal notifications system for texts and missed calls, including popups, led management, and sounds. See NOTIFICATIONS.
  • Miscellaneous: Screen rotation, camera. See MISC.
  • Multiple devices: sxmo supports many different kinds of devices, and users can easily add more. See DEVICES.
  • Environmental variables: sxmo has a lot of environmental variables for configuration purposes. Users can override these with their own preferences. See ENVIRONMENT.

And more (not documented here):

  • SSH as a first class citizen: Log into your phone over ssh and have full access to all sxmo menus and functionality.
  • Alpine Linux / PmOS Based Images: postmarketOS’s infrastructure bakes images that bundle sxmo and pmOS (based on Alpine Linux) which keeps things small, simple, and pragmatic.

Sxmo was presented at LibrePlanet 2022, you can watch the video at https://framatube.org/w/dHBrnMQeEt8Mq82KxV4zKm . πŸŽ₯

If you encounter any bugs, want to request features, or have questions. See BUGS AND SUPPORT.


πŸš€ INITIALIZATION πŸš€

Sxmo is typically started via tinydm(1), which launches the window manager of your choice β€” sway(1), dwm(1), or i3(1) β€” by invoking sxmo_swayinit.sh, sxmo_dwminit.sh, or sxmo_i3init.sh respectively. These scripts wrap around a shared sxmo_init.sh. The entry points are referenced from .desktop files in /usr/share/wayland-sessions/ or /usr/share/xsessions. This means you can also use any other display manager that reads from there. You may want to consider another display manager if your device is a multi-user device.

tinydm(1) is a tiny automatic login manager for single user machines, meaning it has no password prompt. For security we always recommend setting up full disk encryption on your device. A password prompt like unl0kr(1) is then provided at boot time to unlock disk encryption and unauthorized users have no access to the system. πŸ”

Note: You can configure the UID in /etc/conf.d/tinydm (on systems using openrc), or using systemctl edit tinydm.service (on systems using systemd). Make sure to change this if you create a custom user. You may switch between the two window managers in the Power Menu if you installed both.

Once the window manager launches, it will execute sxmo_hook_start.sh. Sxmo relies on superd(1) to launch various services from this start hook. See SERVICES. You can edit the start hook to start additional services.

You can edit ~/.config/sxmo/profile to override certain common environmental variables such as background image. This will be loaded for every shell environment. See ENVIRONMENT.

Note that sxmo respects the xdg specification, e.g., $XDG_CACHE_HOME, $XDG_CONFIG_HOME, etc.

HOOKS:

  • sxmo_hook_start.sh β€” what executes on startup
  • sxmo_hook_wallpaper.sh β€” give the displayed wallpaper file path

SEE ALSO: tinydm(1), superd(1)


πŸ“ LOGGING πŸ“

As soon as the system initializes, the following logs will be available in your $XDG_STATE_HOME directory, which usually corresponds to ~/.local/state/:

  • sxmo.log β€” The central log for Sxmo. Various scripts output a message here via the sxmo_log function provided by sxmo_common.sh.
  • tinydm.log β€” Contains standard error output from various programs running in your sessions if you are using tinydm(1).
  • superd.log β€” Logs the start of various sxmo (and other) background processes on systems that use superd. See SERVICES.

πŸ› οΈ SERVICES πŸ› οΈ

Sxmo starts various background services, depending on your device and configuration. These are managed by a service manager such as superd(1) or systemd(1). You can get an overview by running superctl status.

The services are typically installed in /usr/share/sxmo/configs/services or /usr/share/sxmo/configs/external_services. The difference between the two is that the latter services are for programs that aren’t provided by sxmo-utils, and often conflict with (systemd) services already provided by distributions other than Alpine/postmarketOS. Depending on your distribution, they may not be used.

  • bonsaid β€” manages the logic for the hardware buttons, and invokes sxmo_hook_inputhandles.sh on presses.
  • dunst β€” dunst(1) is our notification daemon.
  • geoclue-agent β€” Proxy location data to map applications.
  • mmsd-tng β€” mmsd-tng(1) manages incoming MMS messages.
  • pipewire β€” pipewire(1) is a media server.
  • pulseaudio β€” pulseaudio(1) is a sound server.
  • sxmo_autosuspend β€” Manages automatic suspension after a certain idle time.
  • sxmo_bg β€” Sets the wallpaper, invokes sxmo_hook_wallpaper.sh to obtain the wallpaper filename.
  • sxmo_battery_monitor β€” This script monitors the battery status using upower(1) and ensures the status bar is updated accordingly.
  • sxmo_brightness β€” Adjust screen brightness
  • sxmo_conky β€” Starts conky (desktop widget)
  • sxmo_desktop_widget β€” Starts the desktop widget via sxmo_hook_desktop_widget.sh .
  • sxmo_hook_lisgd β€” Invokes sxmo_hook_startlisgd.sh which launches the gesture daemon.
  • sxmo_menumode_toggler β€” Configures hardware buttons for sway in menus.
  • sxmo_modemmonitor β€” The modemmonitor observes the modem for incoming calls, texts and other status changes. It is powered by mmcli(1) and dbus_monitor(1) and required to receive calls and texts. It can be toggled via the Config Menu.
  • sxmo_networkmonitor β€” The network monitor looks out for new wifi/mobile connections. It is powered by nmcli(1) and dbus_monitor(1).
  • sxmo_notificationmonitor β€” Monitors for notifications and dispatches them to the notification daemon (sxmo_notifs.sh monitor)
  • sxmo_soundmonitor β€” Monitors audio setup changes and updates the status bar accordingly.
  • sxmo-x11-status β€” This periodically sets the status bar content on Xorg.
  • sxmo_xob β€” A lightweight overlay volume/backlight/progress/anything bar for Xorg
  • sxmo_wob β€” A lightweight overlay volume/backlight/progress/anything bar for Wayland
  • unclutter β€” Hides the mouse pointer when not in use.
  • vvmd β€” vvmd(1) is a lower-level daemon to receive visual voicemail.
  • wireplumber β€” Session/policy manager for pipewire(1).

SEE ALSO: superctl(1)

πŸͺ HOOKS πŸͺ

Okay so bestie, this is the part where it gets good. A whole lot of the functionality lives in hooks (sxmo_hook_*.sh), and once you get hooks, you get Sxmo. Fr fr.

Hooks are tied to specific events β€” like when the system starts up, when a call comes in, or when you open a menu. The core system calls them, and other hooks can call them too. It's giving little event-driven besties ✨

Here's the important bit: Sxmo uses $PATH to figure out which hook actually runs. It looks first for your own user-provided hooks in ~/.config/sxmo/hooks/, and only then does it go looking in /usr/share/sxmo/default_hooks/ for the system defaults. Concrete example, since examples ate: if you pick up a call and ~/.config/sxmo/hooks/sxmo_hook_pickup.sh doesn't exist, then /usr/share/sxmo/default_hooks/sxmo_hook_pickup.sh will be the one that runs. 🫢

Hooks (and config files, too) are versioned with a version hash in a comment. So after you upgrade your installation, you'll be asked to run sxmo_migrate.sh(1) so it can consolidate any new changes from our side with your own modifications. Peep the UPDATING section for that.

You can manually copy and edit hooks to your liking, absolutely, but sxmo_hookmenu.sh (MENU > config > hooks) makes that whole process so much simpler. Use the menu, bestie, it's there for you πŸ’…

Heads up: hooks do not have their own man pages. Instead, each hook is documented in the comment header of that hook itself, which also explains any possible parameters that get passed to the hook. Check the header. Always check the header. πŸ™ˆ

A list of all available hooks in alphabetical order is provided below:

  • sxmo_hook_apps.sh β€” Runs when display of the App menu is requested. Lets you override the apps displayed.
  • sxmo_hook_block_suspend.sh β€” Runs when the system wants to suspend, and it contains the rules that check whether suspension may actually happen or should be blocked because certain programs are active.
  • sxmo_hook_contextmenu.sh β€” Runs when a menu is loaded and an application is active. This hook defines all the context menus, so you can override or add menus for applications right here.
  • sxmo_hook_desktop_widget.sh β€” Runs when the system starts, to launch a desktop widget. Used to display the clock via conky(1).
  • sxmo_hook_discard.sh β€” Runs asynchronously when you discard an incoming call. Stops the ringing hook.
  • sxmo_hook_hangup.sh β€” Runs when the user ends an incoming call.
  • sxmo_hook_icons.sh β€” Runs every time we load a script. This is where you can override icons.
  • sxmo_hook_inputhandler.sh β€” Runs when a gesture is to be interpreted. This defines all kinds of actions that may be triggered by gestures.
  • sxmo_hook_lisgdstart.sh β€” Runs when start of the gestured daemon (lisgd(1)) is requested. This hook lets you define custom gestures.
  • sxmo_hook_lock.sh β€” Runs when the system enters a locked state, where typically the screen is still on but input is off. This is NOT the state lockers like peanutbutter(1) use. Important distinction, don't get it twisted πŸ’€
  • sxmo_network_down.sh β€” Runs after disconnecting from a network. Called by sxmo_networkmonitor.sh.
  • sxmo_network_up.sh β€” Runs after connecting to a new network. Called by sxmo_networkmonitor.sh.
  • sxmo_hook_network_pre_down.sh β€” Runs when a network prepares to go down. Called by sxmo_networkmonitor.sh.
  • sxmo_hook_network_pre_up.sh β€” Runs when a network prepares to go up. Called by sxmo_networkmonitor.sh.
  • sxmo_hook_notification.sh β€” Runs when a notification is received. Runs once for each notification. May be used for forwarding the notification over a network. Called by the notification monitor (sxmo_notifs.sh monitor).
  • sxmo_hook_notifications.sh β€” Runs when the number of notifications changes, i.e. a new one comes in or they all get cleared. This is used for generic things like enabling a LED or playing a sound. Called by the notification monitor (sxmo_notifs.sh monitor).
  • sxmo_hook_missed_call.sh β€” Runs when an incoming call was missed (not picked up). Stops the ringing hook. Called by the modem monitor (sxmo_modemmonitor.sh).
  • sxmo_hook_modem.sh β€” Runs when the modem changes state, used for example to pop up the PIN entry menu. Can be overridden to provide a PIN automatically. Called by the modem monitor (sxmo_modemmonitor.sh).
  • sxmo_hook_mute_ring.sh β€” Runs when the user requests to mute an incoming call. Stops the ringing.
  • sxmo_hook_pickup.sh β€” Runs when the phone accepts an incoming call. This is used to stop the ringing.
  • sxmo_hook_postwake.sh β€” Runs after waking for suspension.
  • sxmo_hook_scripts.sh β€” Runs when display of the Scripts menu is requested. Lets you override the scripts displayed.
  • sxmo_hook_sendsms.sh β€” Runs after you just sent a text message.
  • sxmo_hook_sms.sh β€” Runs when a message (sms/mms/vmm) is received.
  • sxmo_hook_restart_modem_daemons.sh β€” Runs when a restart of the modem is requested.
  • sxmo_hook_ring.sh β€” Runs asynchronously when the phone receives an incoming call, and is used to play a ring tone. It gets stopped again by other hooks (sxmo_hook_pickup.sh, sxmo_hook_discard.sh, sxmo_missed_call.sh, sxmo_hook_mute_ring.sh) and it's called by the modem monitor (sxmo_modemmonitor.sh).
  • sxmo_hook_rotate.sh β€” Runs just after the screen was rotated (explicitly).
  • sxmo_hook_start.sh β€” Runs upon system start in order to start various background services.
  • sxmo_hook_statusbar.sh β€” Runs to update one of the components of the statusbar.
  • sxmo_hook_stop.sh β€” Runs after the system has been stopped, in order to do some cleanup.
  • sxmo_hook_suspend.sh β€” Runs when the system suspends. The actual suspension call is in here.
  • sxmo_hook_tailtextlog.sh β€” Runs when viewing incoming text messages for a given contact.
  • sxmo_hook_unlock.sh β€” Runs when the system becomes unlocked again, i.e. the screen is on and responsive again. This state is NOT the state that screen lockers like peanutbutter(1) enter after unlocking. Again: different thing, don't mix them up 🫢

In further sections of this documentation, all hooks relevant to the topic in question will be mentioned. So keep an eye out πŸ‘€

SEE ALSO: sxmo_migrate.sh(1)


🌈 STATUSBAR 🌈

The bar up at the top of your screen shows off the various workspaces you have available, and they come in the form of the numbers 1,2,3,4 (inactive workspaces are not shown, so it's not cluttered, we love that). Tap one of those numbers and it takes you straight to that workspace. Iconic navigation, honestly.

If you're running dwm rather than sway, right next to that you'll see the layout that's activated. The default layout is a vertical stack (three lines). On sway you may see a dedicated input mode indicated with a red background β€” such as "menu" when you open a menu. The center of the bar is the title of the active window. Main character energy, obviously. πŸ‘‘

The right part of the bar is the statusbar, powered by sxmobar(1). It presents status icons for the following:

  • GSM modem state icon (i.e. what state modemmanager reports, e.g. registered, initializing, etc.)
  • GSM network type icon (e.g. 2g, 3g, etc.).
  • GSM network strength icon.
  • Wifi icon (representing strength).
  • Battery icon (representing strength).
  • Microphone icon (enabled or disabled).
  • Sound icon (or headphone).
  • An icon that also represents what "state" the device is in: unlock (open circle), lock (circle with slash), screenoff (filled circle), or proximity lock (circle with dot).
  • Time.

HOOKS: sxmo_hook_statusbar.sh (override look and feel of the statusbar), sxmo_hook_icons.sh (adjust icons)

SEE ALSO: sxmobar(1)

✨ INPUT ✨

Okay bestie, so like β€” the main forms of input are Hardware buttons (power, raise volume, lower volume), Touchscreen (i.e., touching the screen), and Gestures (i.e., swipes). Sxmo also allows input for a Hardware keyboard (e.g., the pinephone keyboard case or a bluetooth keyboard) and a Stylus. Sxmo also supports a virtual keyboard (svkbd(1) on Xorg or wvkbd(1) on Wayland). Literally so many ways to talk to your phone πŸ’…


πŸŽ€ HARDWARE BUTTONS πŸŽ€

On devices with three buttons (power, volume raise, volume lower), the default button bindings are:

Volume Raise:

  • 1 tap: Launch Main Menu if no app open or Context Menu if app open.
  • 2 taps: Launch Main Menu
  • 3 taps (or hold): Launch Window Management Menu

Volume Lower:

  • 1 tap: Toggle virtual keyboard
  • 2 taps: Toggle the window manager layout state (between monocle/tile/bstack)
  • 3 taps (or hold): Kill app

Power button:

  • 1 tap: Transition to next state
  • 2 taps: Transition to state after next state
  • 3 taps (or hold): Launch terminal

On devices with one button (power), the default button bindings are different. Please refer to sxmo_hook_inputhandler.sh for the exact details.

HOOKS: sxmo_hook_inputhandler.sh (override input handling behavior)


πŸ¦‹ TOUCHSCREEN πŸ¦‹

Sxmo relies on sway(1) or dwm(1) to handle the touchscreen. You can enable/disable touchscreen input via the Config Menu. Slay 🫢


🌸 GESTURES 🌸

Sxmo relies on lisgd(1) for gestures. You can enable/disable gestures via the Config Menu.

These gestures are sensitive to the edge of the screen where the gesture is initiated or where they end up, and some are sensitive to the length/distance of the swipe. Gestures in the main part of the screen, staying clear of the edges, are usually not interpreted and passed to the underlying application unmodified (assuming it has gesture support). iykyk ✨

The default gestures are visualized in the following schematic:

https://man.sr.ht/~anjan/sxmo-docs/assets/sxmo_gestures.png

The default swipe gestures are:

  • 1 finger right-to-left from right edge: Focus next tag/workspace
  • 1 finger left-to-right from left edge: Focus previous tag/workspace
  • 2 fingers right-to-left (anywhere): Move focused application to previous tag/workspace
  • 2 fingers left-to-right (anywhere): Move focused application to next tag/workspace
  • 1 finger top-to-bottom along the left edge (held pressed): Volume down
  • 1 finger bottom-to-top from the top edge: Show the application menu
  • 2 finger bottom-to-top from the top edge: Show the system menu
  • 1 finger top-to-bottom onto the top edge: Close the active menu
  • 1 finger bottom-to-top from the bottom edge: Show virtual keyboard
  • 1 finger top-to-bottom onto the bottom edge: Hide virtual keyboard
  • 2 finger top-to-bottom onto the bottom edge: Close the current active window
  • 3 finger top-to-bottom onto the bottom edge: Kill the current active window
  • 1 finger from bottom-right corner, swiping diagonally: Rotate the screen
  • 1 finger from bottom-left corner, swiping diagonally: Lock the device
  • 1 finger left-to-right along the top edge (held pressed): Increase screen brightness
  • 1 finger right-to-left along the top edge (held pressed): Decrease screen brightness

There are various default gestures that translate to keypresses for the underlying application, this facilitates navigation in a variety of applications, including terminal-based applications, without needing the virtual keyboard:

  • 1 finger right-to-left onto the left edge: Send Left arrow
  • 1 finger left-to-right onto the right edge: Send Right arrow
  • 1 finger top-to-bottom along the right edge (held pressed): Send Key down (scroll down)
  • 1 finger bottom-to-top along the right edge (held pressed): Send Key up (scroll up)
  • 1 finger right-to-left along the bottom edge: Send Backspace
  • 1 finger left-to-right along the bottom edge: Send Return

HOOKS: sxmo_hook_lisgdstart.sh (controls how lisgd is started and what the default gestures are), sxmo_hook_inputhandler.sh defines the avarious actions.

SEE ALSO: lisgd(1)


πŸ’œ VIRTUAL KEYBOARDS πŸ’œ

A virtual keyboard is essential on mobile devices that lack a hardware keyboard. We use wvkbd(1) on Wayland and svkbd(1) on Xorg. They contain layouts specialized for mobile devices and suitable for a variety of international scripts. Iconic behavior fr πŸ’…

The default gesture to show the keyboard is to swipe up from the bottom edge. The default gesture to hide the keyboard is to swipe down onto the bottom edge. The default hardware key to toggle the keyboard is the volume down button.

Note that with both svkbd and wvkbd, you decide when the keyboard hides and shows. It does not pop up automatically on selection of text input fields. 😭

SEE ALSO: wvkbd(1) or svkbd(1).


🧚 HARDWARE KEYBOARD 🧚

If you have a hardware keyboard such as the pinephone keyboard case this should work out-of-the-box. If you have a bluetooth keyboard, see BLUETOOTH.

TODO: Describe dwm/sway bindings?


⭐ STYLUS ⭐

Sxmo relies on sway(1) or dwm(1) to handle stylus input. You can enable/disable stylus input from the Config Menu.


Menus are a central feature of sxmo and are navigable through using hardware buttons. On three button devices:

  • Volume Raise (upper button): Previous item
  • Volume Lower (lower button): Next item
  • Power: Select item

You can also simply use the touchscreen to tap your selection if you'd like as well. Main character energy honestly πŸ‘‘

The menu backend can be configured via the $SXMO_MENU environment variable, which you can set in your ~/.profile. Supported menu backends are:

  • dmenu (only for Xorg)
  • bemenu
  • wofi (Wayland only)

All are mediated via sxmo_dmenu.sh(1).

Note that you can also make full use of the menu system when you are connected over SSH, just run sxmo_appmenu.sh(1) to start the main menu! When running in the tty, bemenu will always serve as backend. No cap 🫢

In addition to a Main Menu, each application can have its own Context Menu associated with it which defines functions unique to that application (e.g., zoom in, zoom out, etc.).

If no application is focused, swiping down from the top of the screen, or pressing the volume raise button once, will bring up the Main Menu. If an application is focused, this will bring up the application's Context Menu instead. (To access the Main Menu while an application is focussed, press the volume raise button twice.)

You can close any open menu with a gesture: swipe straight up (vertically) onto the top edge of the screen and all the open menus will close. See INPUT.

HOOKS: sxmo_hook_apps.sh (what shows up on Apps submenu), sxmo_hook_scripts.sh (what shows up in Scripts submenu), sxmo_hook_contextmenu.sh (controls the content of all the menus, including contextmenus), sxmo_hook_icons.sh (icons)


🌈 SCRIPTS MENU 🌈

The scripts menu includes some scripts that go well with Sxmo and provide various functionality. Some are included out of the box:

  • Web Search: Search duckduckgo with the query provided by the user (bangs work too) (sxmo_websearch.sh)
  • Timer: A simple countdown timer script that vibrates the phones upon completion (sxmo_timer.sh)
  • Screenshot: Take a screenshot of the screen or a portion thereof (sxmo_screenshot.sh)
  • Youtube: Search youtube by keyword via a menu and then view in mpv, script based on idiotbox (https://codemadness.org/idiotbox.html. (sxmo_youtube.sh)
  • Youtube (audio): Like above, but audio-only
  • Weather: United States weather forecast (by zipcode) menu script
  • RSS: Aggregates RSS feeds and let's you view by timespan menu script (based on sfeed(1)

To add your own custom userscripts, you have two options: edit the ~/.config/sxmo/userscripts file or place a shell script in the ~/.config/sxmo/userscripts/ directory.

  • Option 1. Edit ~/.config/sxmo/userscripts and write your entries in it, following the appmenu format <icon> <name> ^ <should-return-to-menu> ^ <script-path-or-command> one entry per line. Example:
$icon_wtr Weather ^ 0 ^ sxmo_terminal.sh -f "Sxmo:size=5" sh -c "curl http://wttr.in/ | less -SR"
  • Option 2. Create the ~/.config/sxmo/userscripts/ directory and place your scripts in it. Note, Userscripts should be set to be executable. You can set a title for the script by adding a comment line of the following ofrmat near the top of the file:
# title="$icon_glb My World"

For examples of scripts sxmo users have made for their mobile devices, see:

https://git.sr.ht/~anjan/sxmo-userscripts

New submissions are welcome there. πŸ’–

HOOKS: sxmo_hook_scripts.sh (control how userscripts are loaded)


πŸ“ APPS MENU πŸ“

The application menu displays a curated list of applications, provided they are installed on your system. If you use wofi as your menu backend ($SXMO_MENU) or if you have j4-dmenu-desktop(1) installed you also have an "All Apps" menu entry that scans *.desktop files dynamically. It's giving ✨ efficiency ✨

HOOKS: sxmo_hook_apps.sh (control list of apps)


πŸŽ€ FILE BROWSER πŸŽ€

A simple menu-based file browser.

SEE sxmo_files.sh(1).


πŸ¦‹ CONFIG MENU πŸ¦‹

The configuration menu provides access to various toggles for enabling, disabling background services.

Further configuration is done using environment variables which are set in ~/.config/sxmo/profile. See ENVIRONMENT. Various tools can also be configured through specific configuration files. In most cases, this comes down to editing a simple configuration in your favourite text editor. Lowkey cozy 🫢


πŸ’… WINDOW MANAGEMENT πŸ’…

Sxmo uses tiling window managers such as sway(1) and dwm(1). This makes a particularly good fit on mobile devices where screen estate is sparse, as windows are automatically laid out to make maximum use of the available space. Ate, no crumbs 🍽️

Window management is done using menus. When you do a long press on the volume up hardware button, the window management menu will pop up and allow to switch layouts when multiple windows are open, and to close windows.

Windows can also be conveniently closed via a quick gesture; move with two fingers down onto the bottom edge of the screen to close the focussed window. Focussing windows is done by simply tapping them on the touchscreen.

πŸ’œ STATES AND SUSPENSION πŸ’œ

okay so sxmo lowkey has a whole personality system and it's called states. there are five basic ones and you need to know them, bestie, because this is literally the whole vibe of the phone:

  • Unlocked (unlock) β€” screen is on, touchscreen is enabled. living your best life.
  • Locked (lock) β€” screen is on, but touchscreen is disabled. you can look, not touch 🫢
  • Screenoff (screenoff) β€” screen is off, touchscreen disabled. also the LED will blink purple every few seconds so you know you're in this state. she's giving ✨ ambience ✨
  • Proximity Lock (proximitylock/unlock) β€” when the phone is close to your face, the screen goes off and the touchscreen is disabled; when it's far from your face, the screen comes on and the touchscreen is enabled. this is the phone-call special, fr fr.
  • Suspend β€” the device is asleep in a low-power mode. πŸ’€

there's a whole schema showing how you slide between states, and it's iconic:

https://man.sr.ht/~anjan/sxmo-docs/schemas/lock-power-states.png

some devices have their own whole workflow and honestly? valid of them:

on desktop systems (which is the default mode if a device isn't recognised), there are two states:

  • unlock β€” the default state, no notes.
  • locker β€” a state that means a session locker is running, and it's preventing any interaction with the environment until it's unlocked with a password. πŸ”

on e-ink display devices (e-readers, that whole crowd) we often only have one state:

  • unlock β€” the screen stays on while the device is suspended, which means the power button is only a refresh of the suspension idle timeout, and a way to bring back interactivity. so like, the button isn't really "off", she's just napping with her eyes open 😭

sxmo will also suspend on most devices when this feature is available:

  • suspend β€” in this state, the modem will still be active and monitor for incoming calls/texts but everything else gets suspended. so the phone is asleep but still listening for drama. πŸ’…

🌈 the usual workflow

this is the flow, and honestly once you get it you're a main character:

  • if the phone is in the unlock state (the default when you boot up) and you want to suspend it, tap the power button once. this transitions to the screenoff state, which then automatically transitions to the suspend state unless something is blocking it.
  • if the phone is in the suspend state and you want to wake it up, tap the power button once (to transition to the lock state) and then tap it once again to transition to the unlock state. this is very deliberate on purpose β€” it prevents accidental wakeups in the pocket. your thigh is not in charge here. πŸ™ˆ

⭐ automatic transitions

sxmo also handles automatic transitions from some states into others, because she's proactive like that:

  • it will automatically transition from unlock to screenoff after a certain amount of idleness (120s).
  • it will automatically transition from lock to screenoff after a certain amount of time (8s).
  • it will automatically transition from screenoff to suspend immediately unless something is blocking it.

you can set up suspend blockers in the sxmo_hook_block_suspend.sh hook. ✨

HOOKS: sxmo_hook_postwake.sh (what to do after waking up from suspend state), sxmo_hook_lock.sh (what to do when transitioning into lock state), sxmo_hook_screenoff.sh (what to do when transitioning into screenoff state), sxmo_hook_unlock.sh (what to do when transitioning into unlock state), sxmo_hook_block_suspend.sh (which processes should prevent the system from to into suspension),

SEE ALSO: sxmo_wakelock.sh(1)


πŸŽ€ LOCKSCREEN πŸŽ€

on Wayland, we use peanutbutter(1) as our lockscreen and she ate. this locks the screen and protects it from unauthorized access. it shows the time and status icons when locked. πŸ•

to unlock, the user has to tap any of four quadrants (1 - top left, 2 - top right, 3 - bottom left, 4 - bottom right) in a user-defined order. that sequence is the passphrase, and it's configured via the $PEANUTBUTTER_PASSCODE environment variable. it takes an integer (arbitrary length) where numbers (1-4) correspond to the aforementioned quadrants, in that order. so your secret is literally a number. iconic.

NOTE: the default unlock code is 1132 (top left, top left, bottom left, top right). write it on your hand if you must, bestie πŸ’€

peanutbutter needs to be explicitly installed by the user if you want a lockscreen. it doesn't come enabled by default to prevent users from locking themselves out due to not knowing how it works. genuinely a kindness.

see peanutbutter(1).


🌸 CRONJOBS 🌸

sxmo ensures that cron jobs run and will actively wake the phone from sleep temporarily to this end β€” like a little alarm clock for your little alarm clock ⏰✨

the cron daemon is installed but not enabled in postmarketOS. cron has to be started manually with rc-service crond start and set to start on boot with rc-update add crond default.

we use a little program called mnc(1) to wake the phone up just before the next planned cron job. we also wrap some sxmo logic in sxmo_rtcwake(1) which launches the cronjob and puts the phone back to sleep when finished.

*/15 * * * * sxmo_rtcwake.sh sleep 10

this example will wake the phone up for 10 seconds every 15 minutes. so polite of it.

if you omit sxmo_rtcwake.sh for a job, the system will not wake up from suspension to execute the job. no cap. note that in such cases, you might want to use sxmo_wm.sh execwait instead, as this will set most of the sxmo environment variables, e.g.:

*/15 * * * * sxmo_wm.sh execwait sleep 20

HOOKS: sxmo_hook_mnc.sh (change the program that calculates when to wakeup)

SEE ALSO: sxmo_rtcwake.sh(1), mnc(1)


πŸ’– CALLS AND TEXTING πŸ’–

calling and texting is fully functional and should work out-of-the-box if your device has a supported modem. πŸŽ‰

on devices with a hardware switch such as the pinephone or Librem 5, make sure you have the modem killswitch in the enabled position. yeah, the physical one. check it. also you may need to wait a little bit after booting before modem functionality becomes available β€” she's stretching, give her a sec. 🧚

the scripting behind the scenes works via mmcli(1).

πŸ” UNLOCKING THE SIM πŸ”

as long as your SIM is locked, a lock icon should appear in the status bar. sxmo automatically asks for your SIM's PIN code using a menu. she's got you. πŸ’…

alternatively, you can do so from the command-line as follows:

mmcli -i 0 --pin 1234

you could put this in sxmo_hook_modem.sh, but there is of course a significant security risk involved if your device gets compromised! so like, maybe don't write your PIN in a file, bestie 😭 that's giving "password on a sticky note on the monitor" energy.

HOOKS: sxmo_hook_modem.sh (runs when the modem changes states)

πŸ“ž CALLING AND USSD πŸ“ž

to place a new call, you can use the Dialer entry in the Main Menu. you'll be prompted for a contact or number to dial. once the call connects, a menu will automatically be launched, allowing you hang up or send DTMF tones. push those buttons, diva. πŸ”₯

a proximity lock is automatically enabled that will lock and turn off your screen during a call if you have the phone close to your ear. see STATES.

the Dialer entry also allows you to initiate USSD sessions. if additional input is required during the session, the menu will continue to come up until the session is ended by either the network or yourself, using the menu. it's persistent like that. ✨

HOOKS: sxmo_hook_call_audio.sh (launch programs when a call is initiated and finished)

βœ‰οΈ SENDING TEXTS βœ‰οΈ

to compose a new text message, the Texts entry in the menu has a Send a Text entry (sxmo_modemtext.sh) which first prompts you for a contact (see CONTACTS) or number. πŸ“±

after choosing, the recipient will by default be dropped into your editor (our default is vis(1)) to compose your message. once your message is as you'd like it, exit the editor using ZZ/:wq!. you'll now be taken to a new menu to confirm your message, from which you can edit/send/add recipients/add attachments/cancel the message. so many options, she's versatile πŸ’…

HOOKS: sxmo_hook_sendsms.sh (what to do when sending sms/mms)

SEE ALSO: sxmo_modemsendsms.sh(1)

πŸ“– READING TEXTS πŸ“–

to view existing text message threads you can use the Texts entry in the Main Menu. this menu will let you follow a text file, as it changes, containing your conversation with each number. when a new text is sent or received, the message will automatically be displayed in your standard $PAGER. πŸ‘‘

while displaying the conversation you can pop out a contextual menu with the power up button to reply by text or to start a call with the sender. multitasking icon.

you can also open a "conversation" window with a gesture from the bottom edge. it will open your editor and the virtual keyboard to type your sms. save and close the file to send the sms. a new editor will be opened again to type a new message. it's a whole loop and it works. πŸ¦‹

HOOKS: sxmo_hook_tailtextlog.sh (you can edit this to control the look and feel of view of message text, e.g., colors, etc.)

πŸ”” MONITORING FOR INCOMING CALLS AND TEXTS πŸ””

a vital feature of a working phone is being able to receive new texts and pickup calls. obviously. this functionality is made possible through a script (sxmo_modemmonitor.sh) that monitors the modem activities and vibrates the phone, plays a notification or ringing sound, and blinks the green LED when there is an incoming text/call. πŸ’š

this monitor is automatically run on start but can be disabled via the menu.

while a call is incoming:

  • the phone will ring and vibrate (unless you disabled these in the Audio menu or in your hooks).
  • a green notification LED will be enabled if your device has one.
  • a menu will appear to allow you to pickup the call. you can also discard the call or ignore the call (mute the ring) from that menu. if you missed the menu for any reason, you can always open the global system menu and you'll see a menu entry to pickup the call; of course this is time-sensitive and this menu entry will only be visible while the other party's line is ringing. so like, don't go anywhere πŸ’€

HOOKS: sxmo_hook_call_audio.sh (adjust volume level when starting/ending call), sxmo_hook_discard.sh (if you hangup without answering), sxmo_hook_hangup.sh (if you hangup), sxmo_hook_missed_call.sh (if you miss the call), sxmo_hook_mute_ring.sh (if you tap ignore to ignore the call, i.e., mute the ringing), sxmo_hook_pickup.sh (if you pickup), sxmo_hook_dial.sh (if you dial), sxmo_hook_ring.sh (what to do when ringing)

when a new text message comes in:

  • the phone will play a notification sound and vibrate (unless you disabled these in the Audio menu).
  • a green notification LED will be enabled if your device has one.
  • a popup notification will appear.

for more information on viewing incoming messages: see READING TEXTS.

HOOKS: sxmo_hook_sms.sh(1) (what to do when an sms/mms is received)

🌐 NETWORK CONFIGURATION 🌐

Okay so the Networks menu (sxmo_networks.sh(1)) is giving "one menu to configure them all" energy β€” it's where you go for basically every flavor of network setup. πŸ’…

πŸ“Ά WIFI πŸ“Ά

From the Networks menu, pick Add a WPA network. Bestie, it literally scans everything around you first and lists the SSIDs in a menu, then when you tap one it'll prompt you for the password. Iconic behavior, honestly.

Or, if you're feeling like a main character who wants more, you can launch nmtui(1) for way more in-depth configuration. Go off. ✨

If your device has a wifi killswitch (looking at you, Pinephone and Librem 5 πŸ‘€), make sure the switch is in the enabled position. That's it, that's the tip.

HOOKS: sxmo_hook_network_up.sh (what to do when network goes up), sxmo_hook_network_down.sh (what to do when network goes down), sxmo_hook_network_pre_up.sh, sxmo_hook_network_pre_down.sh

πŸ“‘ MOBILE DATA πŸ“‘

Mobile data (GSM) can be added via the Networks Menu (sxmo_networks.sh). It will ask for an APN β€” that's it. It's a wrapper around nmcli(1), iykyk. 🫢

πŸ’Œ CONFIGURING MMS πŸ’Œ

To configure MMS, go to Config.

MMS messaging should work exactly like regular text messaging, no cap. When you Send a Text there will be an option to add multiple recipients or attachments. To make mms work, sxmo relies on mmsd-tng(1). The main configuration will be located in ~/.mms/modemmanager/mms. To make things easier in sxmo, we have a dedicated menu entry in Config called Config MMS. This menu will create a default config, and then you can edit fields one by one. The script should take care of restarting mmsd when closed. Slay. πŸ”₯

Note that you likely will not have to configure mmsd-tng if your settings are already in https://wiki.gnome.org/Projects/NetworkManager/MobileBroadband/ServiceProviders. Consider contributing your own if it is not β€” be the change you want to see in the provider list. ✨

⚠️ important one: your carrier's nameserver must be present in /etc/resolv.conf in order to send/receive mms. This should be automatic. However, sometimes NetworkManager will place the wifi's nameservers above the carrier's nameservers, and since /etc/resolv.conf can only use the first three entries, the carrier's nameservers will not be used. To fix this, you can set dns=none in /etc/NetworkManager/NetworkManager.conf and use a static /etc/resolv.conf instead. The way that this is a whole saga 😭

🚫 BLOCKING NUMBERS 🚫

You can block incoming calls and texts by adding the numbers to ~/.config/sxmo/block.tsv (this filename is actually stored in $SXMO_BLOCKFILE). Its syntax is the same as the contacts file. See CONTACTS below. Bye bestie, blocked. πŸ’€


πŸ’– CONTACTS πŸ’–

The sxmo contacts system is based on a plain TSV file that can be placed at ~/.config/sxmo/contacts.tsv (the actual filename is actually kept in the $SXMO_CONTACTFILE environment variable, here we assume the default). Yes, "actually" twice, the manpage is being emphatic about it, we respect it. πŸŽ€

This TSV file is expected to have two tab separated columns: phonenumber, and contactname. Upon receiving a call, if you have a contact stored associated with the incoming number, the contact name will be displayed instead of the number. Contact names will also appear in the Texts and Dialer menus if they are present in the contacts TSV file. If no contacts.tsv is present, or the number is missing from this file, the contact in menus will show up as ???. Mysterious. Enigmatic. Lowkey giving ghost. πŸ‘»

A contacts.tsv example might look like:

    +122345628     John Smith
    +128371642     Jeff Foo
    +31612345678   Jan Janssen

You may edit the file in an editor of your choice, or use the New Contact entry from the Contacts menu. Both are valid, both are slay. πŸ’…

SEE ALSO: sxmo_contacts.sh(1), sxmo_contactmenu.sh(1)

πŸ”Š AUDIO πŸ”Š

You can use the Audio Menu (sxmo_audio.sh) to toggle which audio output you want to send sound to. Sxmo uses pipewire(1) and pulseaudio(1). We use callaudiod(1) to route audio during a phone call. That's the whole stack, bestie. 🫢

πŸ’€ the sad part: currently, bluetooth audio during phone calls does not work. Please see: - https://gitlab.com/mobian1/issues/-/issues/345 - https://gitlab.com/mobian1/callaudiod/-/issues/12
SEE ALSO: sxmo_hook_call_audio.sh (adjust volume after/before a call)

πŸ¦‹ BLUETOOTH πŸ¦‹

To enable bluetooth, toggle it in Config. A Bluetooth Menu (sxmo_bluetoothmenu.sh) can be chosen from the Main Menu. Pairing szn ✨


πŸ”„ UPDATING πŸ”„

Sxmo's packages are typically distributed via your Linux distribution (e.g. postmarketOS). To update run:

sxmo_upgrade.sh

...or just use the menu entry within the Config Menu, which does the same thing. This is a tiny wrapper that invokes your distribution's package manager. No magic, no tricks, just vibes and apk/pacman/whatever your distro fave is. πŸ’…

After you update the sxmo packages themselves, be sure to run sxmo_migrate.sh(1) to guide you through upgrading your (local) config files and hooks, if needed. Heads up: your configuration files and hooks may be temporarily stashed away until you complete the migration process. This is so the system can remain fully functional at all times. See sxmo_migrate.sh(1) for further documentation on this. Don't panic if your config ghosts you for a sec, it comes back. 😭

New releases will be announced on the ~mil/sxmo-announce@lists.sr.ht mailing list. See https://lists.sr.ht/~mil/sxmo-announce for the archives. Mail ~mil/sxmo-announce+subscribe@lists.sr.ht to automatically subscribe. Newsletter besties rise up 🫢

SEE ALSO: sxmo_migrate.sh(1)

πŸ”” NOTIFICATIONS πŸ””

When a notification comes in, the status bar will indicate this with an icon, and the menu will have a Notifications entry that also mentions the number of unread notifications. They can be viewed and cleared through this submenu. Clean slate energy, we love to see it. ✨

If your device has a green status LED, it will be default be enabled when you have unread notifications. Yes, a little green light to gently judge you. πŸ’š

Notifications are mediated by sxmo_notifs.sh. Whenever a notification comes in or is cleared, then sxmo_hook_notifications.sh will be called with the number of notifications. This puts an icon status in the status bar if there are any notifications. For each specific notification, sxmo_hook_notification.sh is called. This hook can be used, for instance, to forward the notification content over a network. Cute AND useful, honestly obsessed. πŸŽ€

HOOKS: sxmo_hook_notifications.sh (runs when there is any notification), sxmo_hook_notification.sh (runs once for each notification)

πŸ“± DEVICES πŸ“±

This section describes how to add a new device to sxmo. If you are instead looking for what devices are suitable to run Sxmo, then check the postmarketOS device page at https://wiki.postmarketos.org/wiki/Devices instead. Different question, bestie. πŸ’…

When adding a new device, there are three basic steps:

  1. Determine the $SXMO_DEVICE_NAME
  2. Add a sxmo_deviceprofile_${SXMO_DEVICE_NAME}.sh file to scripts/deviceprofiles/ in the sxmo-utils source tree. Please send us the patch too. πŸ™

(Yes, that's two bullets for "three basic steps" in the original β€” we're not gonna fix it, we're just gonna love it as it is. 😭)

πŸ” FINDING THE SXMO_DEVICE_NAME πŸ”

The $SXMO_DEVICE_NAME is determined by the following code in sxmo_init.sh upon boot:

tr -c '0[:alnum:].,-' '_' < /proc/device-tree/compatible | tr '0' 'n' | head -n1

Run it, look at the output, that's your name. Slay. ✨

πŸ“ ADDING A DEVICEPROFILE FILE πŸ“

In the sxmo-utils source tree, navigate to scripts/deviceprofiles/ and make a file called sxmo_deviceprofile_${SXMO_DEVICE_NAME}.sh. This file should contain various environment variables that define things unique to your device, e.g. input ids, etc. There is a README.md in the same directory that will help. Read the README, bestie, it's there for you. 🫢

πŸŽ›οΈ DEVICE PROFILE VARIABLES πŸŽ›οΈ

The following variables are used in device profiles, see DEVICES.

  • SXMO_DISABLE_KEYBINDS (input) β€” If set, this disables most custom Sxmo binds on the volume keys.
  • SXMO_LISGD_THRESHOLD (input) β€” Threshold for detecting touches [default: 125]
  • SXMO_LISGD_THRESHOLD_PRESSED (input) β€” Threshold for detecting long presses [default: 60]
  • SXMO_LISGD_INPUT_DEVICE (input) β€” Input device [default: /dev/input/by-path/first/touchscreen]
  • SXMO_MIN_BRIGHTNESS (display) β€” Minimum brightness level (default: 5)
  • SXMO_MODEM_GPIO_KEY_RI (modem) β€” If the modem driver handles gpio, sxmo has to know to disable the events from this input source. This is the name of the input device.
  • SXMO_MONITOR (display) β€” The name of the output device for the primary display (e.g. DSI-1). The output can be found with swaymsg -t get_outputs or xrandr when running dwm.
  • SXMO_NO_VIRTUAL_KEYBOARD (input) β€” If defined, all virtual keyboard management is disabled, and some related gesture behavior is changed.
  • SXMO_NO_MODEM (modem) β€” Define this if your device has no modem, modem-related functionality will be disabled.
  • SXMO_POWER_BUTTON (input) β€” Power button "Identifier" from swaymsg -t get_inputs command.
  • SXMO_ROTATE_DIRECTION (display) β€” The direction to rotate when using the gesture [default: right]
  • SXMO_ROTATE_START (display) β€” Should the display rotate on start? (useful when the device is landscape by default)
  • SXMO_STATES (states) β€” Space separated list of states this device can be in. See STATES.
  • SXMO_STYLUS_ID (input) β€” ID (from xinput) for the stylus device [DWM-ONLY] [default: 10]
  • SXMO_SUSPENDABLE_STATES (states) β€” The list of suspendable states, with their timeout duration [default: "screenoff 3"]
  • SXMO_TOUCHSCREEN_ID (input) β€” ID (from xinput) for the touchscreen device [DWM-ONLY] [default: 10]
  • SXMO_VIBRATE_DEV (misc) β€” Path to vibration device (see sxmo_vibrate.c and clickclack.c) [default: /dev/input/by-path/platform-vibrator-event]
  • SXMO_VIBRATE_STRENGTH (misc) β€” Strength parameter to pass to sxmo_vibrate [default: 1]
  • SXMO_VOLUME_BUTTON (input) β€” Volume button "Identifier" from swaymsg -t get_inputs command. If the volume up identifier ($VOL_UP_ID) is different from the volume down identifier ($VOL_DOWN_ID), set $SXMO_VOLUME_BUTTON="$VOL_UP_ID $VOL_DOWN_ID". See for example the sxmo-utils/scripts/deviceprofiles/sxmo_deviceprofile_xiaomi,beryllium.sh file.
  • SXMO_WOFI_SMALLSCREEN (display) β€” Can be set to 0 on devices like laptops and desktops which do not have a small screen and to 1 on mobile device with smaller screens. On smaller screens, wofi will be configured to more efficiently make use of the screen real estate. [default: 1 or unset]

🌈 MISC 🌈

This section explains some smaller miscellaneous aspects of Sxmo. The little guys. The side quests. 🧚

πŸ”„ ROTATION πŸ”„

Rotating the screen (from portrait to landscape) can be done either automatically or manually. Automatic rotation can be enabled or disabled via the Config Menu. The sxmo_rotate.sh script performs the actual rotation. It's the one doing the work, we just press buttons. πŸ’…

A default gesture is also available to rotate: swipe from the bottom-right corner towards the center. Fancy hands, go. ✨

πŸ”¦ FLASHLIGHT πŸ”¦

If your device has a flashlight, you can toggle it via the main menu. Late-night snack retrieval: enabled. πŸ“

πŸ“· CAMERA πŸ“·

If your device has a suppored camera, you can launch a viewer to take photos and videos via the main menu. (Yes, "suppored" β€” we quote the manpage faithfully, typos and all, that's the brand. πŸŽ€)

🌸 ENVIRONMENT 🌸

okay so bestie, the first hint is literally just: type env to see environmental variables πŸ‘€. Those variables can be overridden (generally) in ~/.config/sxmo/profile or ~/.profile. Also peek at ~/.Xdefaults, ~/.config/sxmo/xinit, and ~/.config/sxmo/sway.

sxmo respects the XDG protocol and falls back to some sane defaults if that’s missing on your system. The most relevant ones are:

  • XDG_DATA_HOME β€” ~/.local/share
  • XDG_CONFIG_HOME β€” ~/.config
  • XDG_CACHE_HOME β€” ~/.cache
  • XDG_STATE_HOME β€” ~/.local/state
  • XDG_RUNTIME_DIR β€” /dev/shm/$USER/1000
  • XDG_DATA_DIRS β€” ~/.local/share

The default values for environment variables are set in /etc/profile.d/sxmo_init.sh. If you want to override them, use your ~/.profile. Sxmo itself defines these variables, in alphabetical order:

  • DEFAULT_COUNTRY β€” String to indicate the default country sxmo should fall back to when phone numbers are not country-code prefixed. It should be set to a country code (ISO-3166) such as FR for France, DE for Germany, US for the United States. See CONTACTS.
  • KEYBOARD β€” the virtual keyboard used; defaults to svkbd-mobile-intl (svkbd(1)) on Xorg, or wvkbd-mobile-intl on Wayland (wvkbd(1)).
  • KEYBOARD_ARGS β€” parameters to pass to the virtual keyboard when it launches.
  • SXMO_BLOCKDIR β€” blocked number metadata (~/.local/share/modem/block).
  • SXMO_BLOCKFILE β€” a file with phone numbers to block (~/.config/sxmo/block.tsv).
  • SXMO_CACHEDIR β€” temporary cache files (~/.cache/sxmo).
  • SXMO_CONTACTFILE β€” a TSV file containing contacts (~/.config/sxmo/contacts.tsv).
  • SXMO_DEBUG β€” if defined, extra debug messages will appear in ~/.local/state/sxmo.log.
  • SXMO_DEFAULT_DRAFT β€” a string containing the default draft text for text messages.
  • SXMO_DEVICE_NAME β€” the device name. Sxmo will also load all the variables in /usr/bin/sxmo_deviceprofile_$SXMO_DEVICE_NAME.sh, such as id for touch input, whether the device has LEDs, and so on. See DEVICES.
  • SXMO_LOGDIR β€” where sxmo logs metadata about calls and texts received. Under this directory there will be several subdirectories, one for each number, which contain the content of the text messages received. (~/.local/share/modem)
  • SXMO_MENU β€” the menu program to use. This must be either dmenu(1), bemenu(1), or wofi(1); you cannot just specify an arbitrary binary here, because Sxmo must have internal support for it.
  • SXMO_NOTCH β€” set SXMO_NOTCH to a string to use for (under) the notch; the length of the string determines the width. Do NOT use spaces or tabs.
  • SXMO_NOTCH_PRIO β€” integer value determining where to place the notch in relation to other sxmobar components. The value is trial and error (default is 29).
  • SXMO_NOTIFDIR β€” the directory where notifications are stored (mediated by sxmo_notifs.sh).
  • SXMO_OS β€” the distribution (postmarketos, archlinux, etc.).
  • SXMO_TERMINAL β€” terminal to launch. Defaults to foot(1) on Wayland or st(1) on Xorg. Launching a terminal is mediated via sxmo_terminal.sh, which reads this variable.
  • SXMO_RINGTONE β€” the audio file to play when the phone is ringing.
  • SXMO_RINGNUMBER β€” the number of times the audio file will play.
  • SXMO_STATE β€” the file containing the current state.
  • SXMO_SWAY_SCALE β€” the scaling factor to use for sway.
  • SXMO_TEXTSOUND β€” the audio file to play when the phone receives a text.
  • SXMO_VIBRATE_STRENGTH β€” the vibration strength to pass to the haptic feedback when a text arrives.
  • SXMO_WM β€” the window manager used (sway or dwm).

Other relevant environment variables are, in alphabetical order:

  • BROWSER β€” default web browser.
  • DMENU_WRAP_AROUND β€” if set to 1, when scrolling past the beginning or end of a menu, it wraps around it (dmenu only).
  • DBUS_SESSION_BUS_ADDRESS β€” dbus socket.
  • BEMENU_OPTS β€” options to pass to bemenu.
  • EDITOR β€” default text editor.
  • MOZ_ENABLE_WAYLAND β€” set to 1 when running under Wayland.
  • PATH β€” the system path. This will be set to look in ~/.config/sxmo/hooks/$SXMO_DEVICE_NAME/, /usr/share/sxmo/hooks/$SXMO_DEVICE_NAME/, ~/.config/sxmo/hooks/, and ~/usr/share/sxmo/hooks/ before the regular PATH the operating system sets.
  • SDL_VIDEODRIVER β€” set to value wayland when running under Wayland.
  • SHELL β€” default shell.
  • SWAYSOCK β€” sway socket.
  • XDG_CURRENT_DESKTOP β€” the current desktop (sway or dwm).

Hint: you can type _sxmo_grab_session from the command line to reload environment variables (e.g., if you switch window managers but are logged in over an ssh connection) πŸ”„.

There are other environmental variables that are device-specific. See DEVICES. As well, several scripts have their own environmental variables which we do not list here.


πŸ—‚οΈ FILES πŸ—‚οΈ

  • ~/.local/state/sxmo.log β€” sxmo’s logfiles. See LOGGING.
  • ~/.config/sxmo β€” most sxmo config files.
  • ~/.config/sxmo/profile β€” profile where you can customise environment variables. See ENVIRONMENT.
  • ~/.config/sxmo/hooks β€” your user-defined hooks. See HOOKS.
  • ~/.config/sxmo/userscripts β€” either a file or a directory containing your userscripts. See MENUS.

πŸ‘‘ AUTHORS πŸ‘‘

Sxmo is developed by a wide community of contributors, to whom we are all grateful 🫢. See the git log for full details.

πŸ’Œ MAINTAINERS πŸ’Œ

  • Anjandev Momi <anjan@momi.ca>
  • Aren Moynihan <aren@peacevolution.org>
  • Maarten van Gompel <proycon@anaproy.nl>
  • Willow Barraco <contact@willowbarraco.fr>

Former maintainers

  • Miles Alan <m@milesalan.com> (the original creator of Sxmo)
  • Peter John Hartman <peterjohnhartman@gmail.com>

πŸ› BUGS AND SUPPORT 🫢

We have the following support channels for questions and bug reports:

  • ~mil/sxmo-announce@lists.sr.ht (e-mail) β€” this is a low-volume read-only mailing list used for announcing new package releases. See https://lists.sr.ht/~mil/sxmo-announce.
  • ~mil/sxmo-devel@lists.sr.ht (e-mail) β€” this is our primary asynchronous developer support channel, where you can send code contributions as patches via git-send-email(1). See https://lists.sr.ht/~mil/sxmo-devel.
  • ~mil/sxmo-user@lists.sr.ht (e-mail) β€” this is our primary asynchronous user support channel, where you can send questions, bug reports, and feature requests. Please check if your question is not already answered before posting. Here you can also discuss the general goals of the project, your experience daily driving, and have other fun discussions with the Sxmo community. See https://lists.sr.ht/~mil/sxmo-user.
  • https://todo.sr.ht/~mil/sxmo-tickets (web) β€” this is our bug/feature tracker. It is for confirmed bugs and tracking feature requests. Not for user support. See https://todo.sr.ht/~mil/sxmo-tickets.
  • #sxmo (IRC) β€” we have the channel #sxmo and #sxmo-offtopic on the OFTC IRC Network (irc.oftc.net). Here you can talk to Sxmo users and developers in realtime. Moreover, you can get help with Sxmo and related projects. Please stay around for answers when asking questions. A web-based chat is available via https://webchat.oftc.net/?channels=#sxmo.
  • #sxmo:postmarketos.org (Matrix) β€” this is a Matrix channel which is bridged to the IRC chat. See https://matrix.to/#/#sxmo:postmarketos.org.
  • PostmarketOS Wiki (web) β€” the postmarketOS Wiki contains user-maintained Tips & Tricks pages for Sxmo like https://wiki.postmarketos.org/wiki/Sxmo/Tips_and_Tricks.
  • There are a number of communities working on FOSS mobile distros, middleware, apps, and hardware development. You can join the other chatrooms related to FOSS mobile via the following matrix space: https://matrix.to/#/#FOSSMobile:matrix.org.

Sxmo is licensed under the GNU Affero General Public License v3.


πŸ”— SEE ALSO πŸ”—

sxmo_appmenu.sh(1) sxmo_files.sh(1) sxmo_migrate.sh(1) sxmo_wakelock.sh(1) lisgd(1) peanutbutter(1) svkbd(1) wvkbd(1)


and that’s the whole sxmo(7) page, bestie πŸ’– source/version: sxmo(7), dated 2026-05-10 β€” go be iconic with ur phone πŸŽ€βœ¨

πŸ“¦ where this page comes from