~ruther/guix-local

65c77e90aac72706736c1cfb596caa16419e88c2 — dan 9 months ago 17e2ab5
gnu: Add home-darkman-service-type.

* gnu/home/services/desktop.scm (home-darkman-configuration)
(home-darkman-service-type): New variables.
(serialize-number, serialize-boolean,
serialize-home-darkman-configuration)
(home-darkman-configuration-files, home-darkman-profile-service)
(home-darkman-shepherd-service): New procedures.
* doc/guix.texi (Desktop Home Services): Document it.

Change-Id: I23acb2cae9745e1a76c19c5552bf487539d6a807
Reviewed-by: Sergey Trofimov <sarg@sarg.org.ru>
Signed-off-by: Sharlatan Hellseher <sharlatanus@gmail.com>
2 files changed, 141 insertions(+), 2 deletions(-)

M doc/guix.texi
M gnu/home/services/desktop.scm
M doc/guix.texi => doc/guix.texi +44 -0
@@ 51852,6 51852,50 @@ is passed to the @code{xorg-start-command-xinit} procedure producing the
@command{startx} used.  Default value is @code{(xorg-configuration)}.
@end defvar

@defvar home-darkman-service-type
This is the service type for the
@uref{https://gitlab.com/WhyNotHugo/darkman, Darkman}, a program for
dark-mode and light-mode transitions on Unix-like desktops.  It invokes
scripts in @code{$XDG_DATA_DIRS/dark-mode.d} at sundown, and invokes
scripts in @code{$XDG_DATA_DIRS/light-mode.d} at sunrise.  Darkman tries
to determine the user's current location from:
@itemize
@item The config file.
@item The cache file from last time it ran.
@item Using the system geoclue.
@end itemize
@end defvar

@deftp {Data Type} home-darkman-configuration
The configuration record for @code{home-darkman-service-type}.  Its
available fields are:

@table @asis
@item @code{darkman} (default: @code{darkman}) (type: file-like)
The @code{darkman} package to use.

@item @code{latitude} (type: maybe-number)
Latitude, used at startup or when @code{use-geoclue} is @code{#f}.  More
than one decimal point is generally not needed.

@item @code{longitude} (type: maybe-number)
Longitude, used at startup or when @code{use-geoclue} is @code{#f}.
More than one decimal point is generally not needed.

@item @code{use-geoclue} (default: @code{#f}) (type: boolean)
Whether to use a local geoclue instance to determine the current
location.  Setting this to false without explicitly setting latitude and
longtitude disables automatic transitions entirely.

@item @code{dbus-server} (default: @code{#t}) (type: boolean)
Whether to expose the current mode via darkman's own D-Bus API.

@item @code{portal} (default: @code{#t}) (type: boolean)
Whether to expose the current mode via the XDG settings portal D-Bus
API.

@end table
@end deftp

@node Guix Home Services
@subsection Guix Home Services

M gnu/home/services/desktop.scm => gnu/home/services/desktop.scm +97 -2
@@ 3,6 3,7 @@
;;; Copyright © 2022 ( <paren@disroot.org>
;;; Copyright © 2023 conses <contact@conses.eu>
;;; Copyright © 2023 Janneke Nieuwenhuizen <janneke@gnu.org>
;;; Copyright © 2025 dan <i@dan.games>
;;;
;;; This file is part of GNU Guix.
;;;


@@ 25,7 26,7 @@
  #:use-module (gnu services configuration)
  #:use-module (gnu services xorg)
  #:autoload   (gnu packages glib)    (dbus)
  #:autoload   (gnu packages xdisorg) (redshift unclutter)
  #:autoload   (gnu packages xdisorg) (darkman redshift unclutter)
  #:autoload   (gnu packages xorg) (setxkbmap xmodmap)
  #:use-module (guix records)
  #:use-module (guix gexp)


@@ 46,7 47,11 @@
            home-xmodmap-configuration
            home-xmodmap-service-type

            home-startx-command-service-type))
            home-startx-command-service-type

            home-darkman-configuration
            home-darkman-configuration?
            home-darkman-service-type))


;;;


@@ 447,3 452,93 @@ buttons under the Xorg display server via user-defined expressions.")))

(define-service-type-mapping
  startx-command-service-type => home-startx-command-service-type)


;;;
;;; Darkman.
;;;

(define-maybe number)

(define (serialize-number field value)
  (string-append (match field
                   ('latitude "lat")
                   ('longitude "lng")
                   (_ (symbol->string field)))
                 ": " (number->string value) "\n"))

(define (serialize-boolean field value)
  (string-append (match field
                   ('use-geoclue "usegeoclue")
                   ('dbus-server "dbusserver")
                   (_ "portal"))
                 ": " (if value "true" "false") "\n"))

(define-configuration home-darkman-configuration
  (darkman
   (file-like darkman)
   "The @code{darkman} package to use.")

  (latitude
   maybe-number
   "Latitude, used at startup or when @code{use-geoclue} is @code{#f}.  More than
one decimal point is generally not needed.")

  (longitude
   maybe-number
   "Longitude, used at startup or when @code{use-geoclue} is @code{#f}.  More than
one decimal point is generally not needed.")

  (use-geoclue
   (boolean #f)
   "Whether to use a local geoclue instance to determine the current location.
Setting this to false without explicitly setting latitude and longtitude
disables automatic transitions entirely.")

  (dbus-server
   (boolean #t)
   "Whether to expose the current mode via darkman's own D-Bus API.")

  (portal
   (boolean #t)
   "Whether to expose the current mode via the XDG settings portal D-Bus API."))

(define (serialize-home-darkman-configuration config)
  (mixed-text-file
   "config.yaml"
   (serialize-configuration config home-darkman-configuration-fields)))

(define (home-darkman-configuration-files config)
  `(("darkman/config.yaml" ,(serialize-home-darkman-configuration config))))

(define (home-darkman-profile-service config)
  (list (home-darkman-configuration-darkman config)))

(define (home-darkman-shepherd-service config)
  (list
   (shepherd-service
     (provision '(darkman))
     (requirement '(dbus))
     (modules '((shepherd support)))      ;for '%user-log-dir'
     (start #~(make-forkexec-constructor
               (list #$(file-append (home-darkman-configuration-darkman config)
                                    "/bin/darkman")
                     "run")
               #:log-file
               (string-append %user-log-dir "/darkman.log")))
     (stop #~(make-kill-destructor)))))

(define home-darkman-service-type
  (service-type
    (name 'home-darkman)
    (extensions
     (list (service-extension home-shepherd-service-type
                              home-darkman-shepherd-service)
           (service-extension home-xdg-configuration-files-service-type
                              home-darkman-configuration-files)
           (service-extension home-profile-service-type
                              home-darkman-profile-service)))
    (default-value (home-darkman-configuration))
    (description "Run the @code{darkman} daemon, which will invoke scripts in
$XDG_DATA_DIRS/dark-mode.d/ when sundown, and invoke scripts in
$XDG_DATA_DIRS/light-mode.d/ when sunrise.")))