summaryrefslogtreecommitdiff
path: root/modules/home-manager/personal
diff options
context:
space:
mode:
Diffstat (limited to 'modules/home-manager/personal')
-rw-r--r--modules/home-manager/personal/default.nix15
-rw-r--r--modules/home-manager/personal/dotfiles/background-imagebin0 -> 581223 bytes
-rw-r--r--modules/home-manager/personal/dotfiles/default.nix11
-rw-r--r--modules/home-manager/personal/dotfiles/latexmkrc5
-rw-r--r--modules/home-manager/personal/dotfiles/rofi.rasi201
-rw-r--r--modules/home-manager/personal/dotfiles/spacemacs.el651
-rw-r--r--modules/home-manager/personal/dotfiles/venv-manager.nix39
-rw-r--r--modules/home-manager/personal/environment.nix20
-rw-r--r--modules/home-manager/personal/gui/default.nix42
-rw-r--r--modules/home-manager/personal/gui/redshift.nix17
-rw-r--r--modules/home-manager/personal/gui/x/default.nix14
-rw-r--r--modules/home-manager/personal/gui/x/i3/bar/default.nix27
-rw-r--r--modules/home-manager/personal/gui/x/i3/bar/i3status.go289
-rw-r--r--modules/home-manager/personal/gui/x/i3/default.nix56
-rw-r--r--modules/home-manager/personal/gui/x/i3/keybindings.nix47
-rw-r--r--modules/home-manager/personal/gui/x/i3/startup.nix25
-rw-r--r--modules/home-manager/personal/gui/x/idlehook.nix22
-rw-r--r--modules/home-manager/personal/profiles.nix157
-rw-r--r--modules/home-manager/personal/programs/alacritty.nix21
-rw-r--r--modules/home-manager/personal/programs/default.nix13
-rw-r--r--modules/home-manager/personal/programs/direnv.nix31
-rw-r--r--modules/home-manager/personal/programs/emacs.nix59
-rw-r--r--modules/home-manager/personal/programs/firefox/default.nix139
-rw-r--r--modules/home-manager/personal/programs/firefox/engines.nix8
-rw-r--r--modules/home-manager/personal/programs/firefox/userjs.nix66
-rw-r--r--modules/home-manager/personal/programs/git.nix21
-rw-r--r--modules/home-manager/personal/programs/rofi.nix8
-rw-r--r--modules/home-manager/personal/programs/thunderbird.nix35
28 files changed, 2039 insertions, 0 deletions
diff --git a/modules/home-manager/personal/default.nix b/modules/home-manager/personal/default.nix
new file mode 100644
index 0000000..dcd7500
--- /dev/null
+++ b/modules/home-manager/personal/default.nix
@@ -0,0 +1,15 @@
+{ ... }:
+
+{
+ imports = [ ./dotfiles ./environment.nix ./gui ./profiles.nix ./programs ];
+
+ # This value determines the Home Manager release that your
+ # configuration is compatible with. This helps avoid breakage
+ # when a new Home Manager release introduces backwards
+ # incompatible changes.
+ #
+ # You can update Home Manager without changing this value. See
+ # the Home Manager release notes for a list of state version
+ # changes in each release.
+ home.stateVersion = "23.05";
+}
diff --git a/modules/home-manager/personal/dotfiles/background-image b/modules/home-manager/personal/dotfiles/background-image
new file mode 100644
index 0000000..4288f3e
--- /dev/null
+++ b/modules/home-manager/personal/dotfiles/background-image
Binary files differ
diff --git a/modules/home-manager/personal/dotfiles/default.nix b/modules/home-manager/personal/dotfiles/default.nix
new file mode 100644
index 0000000..27610ca
--- /dev/null
+++ b/modules/home-manager/personal/dotfiles/default.nix
@@ -0,0 +1,11 @@
+{ ... }:
+
+{
+ personal.home.dotfiles = {
+ wallpaper = ./background-image;
+ latexmkrc = ./latexmkrc;
+ rofi = ./rofi.rasi;
+ spacemacs = ./spacemacs.el;
+ venv-manager = ./venv-manager.nix;
+ };
+}
diff --git a/modules/home-manager/personal/dotfiles/latexmkrc b/modules/home-manager/personal/dotfiles/latexmkrc
new file mode 100644
index 0000000..788ceb7
--- /dev/null
+++ b/modules/home-manager/personal/dotfiles/latexmkrc
@@ -0,0 +1,5 @@
+$clean_ext = 'bbl nav prv_%R.fmt prv_%R.log prv/*/* prv/* prv run.xml snm vrb';
+
+$ENV{'TZ'}='Europe/Paris';
+
+$pdf_previewer = 'evince %O %S 2>&1 | grep -v Gtk-WARNING | grep . 1>&2'; \ No newline at end of file
diff --git a/modules/home-manager/personal/dotfiles/rofi.rasi b/modules/home-manager/personal/dotfiles/rofi.rasi
new file mode 100644
index 0000000..375b28b
--- /dev/null
+++ b/modules/home-manager/personal/dotfiles/rofi.rasi
@@ -0,0 +1,201 @@
+/**
+ * rofi -dump-theme output.
+ * Rofi version: 1.7.0
+ **/
+* {
+ alternate-urgent-background: var(lightbg);
+ alternate-active-foreground: var(blue);
+ selected-active-background: var(actbg);
+ selected-urgent-foreground: var(background-color);
+ hide-scrollbar: "true";
+ padding: 0;
+ normal-foreground: var(text-color);
+ text-color: rgba ( 178, 174, 168, 100 % );
+ line-padding: 2;
+ background: rgba ( 253, 246, 227, 100 % );
+ line-margin: 2;
+ alternate-normal-foreground: var(foreground);
+ urgent-foreground: var(text-color);
+ active-background: var(selbg);
+ selected-normal-background: var(actbg);
+ blue: rgba ( 38, 139, 210, 100 % );
+ selected-urgent-background: var(urgbg);
+ selected-active-foreground: var(winbg);
+ separator-style: "none";
+ separatorcolor: var(foreground);
+ urgbg: rgba ( 229, 57, 53, 100 % );
+ lightfg: rgba ( 88, 104, 117, 100 % );
+ alternate-active-background: var(lightbg);
+ selbg: rgba ( 57, 73, 163, 100 % );
+ spacing: 2;
+ winbg: rgba ( 179, 190, 255, 100 % );
+ actbg: rgba ( 38, 38, 38, 100 % );
+ alternate-urgent-foreground: var(red);
+ margin: 0;
+ lightbg: rgba ( 238, 232, 213, 100 % );
+ red: rgba ( 220, 50, 47, 100 % );
+ background-color: rgba ( 0, 0, 0, 0 % );
+ normal-background: var(background-color);
+ border-color: var(foreground);
+ foreground: rgba ( 0, 43, 54, 100 % );
+ alternate-normal-background: var(lightbg);
+ urgent-background: var(background-color);
+ selected-normal-foreground: var(winbg);
+ active-foreground: var(text-color);
+}
+element {
+ padding: 10px ;
+ cursor: pointer;
+ spacing: 5px ;
+ border: 0;
+}
+element normal.normal {
+ background-color: var(normal-background);
+ text-color: var(normal-foreground);
+}
+element normal.urgent {
+ background-color: var(urgent-background);
+ text-color: var(urgent-foreground);
+}
+element normal.active {
+ background-color: var(active-background);
+ text-color: var(active-foreground);
+}
+element selected.normal {
+ background-color: var(selected-normal-background);
+ border-color: var(active-background);
+ text-color: var(selected-normal-foreground);
+ border: 0px 5px 0px 0px ;
+}
+element selected.urgent {
+ background-color: var(selected-urgent-background);
+ text-color: var(selected-urgent-foreground);
+}
+element selected.active {
+ background-color: var(selected-active-background);
+ text-color: var(selected-active-foreground);
+}
+element alternate.normal {
+ background-color: var(normal-background);
+ text-color: var(normal-foreground);
+}
+element alternate.urgent {
+ background-color: var(urgent-background);
+ text-color: var(urgent-foreground);
+}
+element alternate.active {
+ background-color: var(active-background);
+ text-color: var(active-foreground);
+}
+element-text {
+ background-color: rgba ( 0, 0, 0, 0 % );
+ cursor: inherit;
+ highlight: inherit;
+ text-color: inherit;
+}
+element-icon {
+ background-color: rgba ( 0, 0, 0, 0 % );
+ size: 1.0000em ;
+ cursor: inherit;
+ text-color: inherit;
+}
+window {
+ transparency: "real";
+ padding: 5;
+ width: 10.0000em ;
+ orientation: horizontal;
+ location: west;
+ children: [ mainbox ];
+ background-color: rgba ( 0, 0, 0, 100 % );
+ height: 100.0000% ;
+ anchor: west;
+ border: 1;
+}
+mainbox {
+ padding: 0;
+ spacing: 0.8000em ;
+ border: 0;
+ children: [ entry,listview ];
+}
+message {
+ padding: 1px ;
+ border-color: var(separatorcolor);
+ border: 2px dash 0px 0px ;
+}
+textbox {
+ text-color: var(foreground);
+}
+listview {
+ fixed-height: 0;
+ padding: 2px 0px 0px ;
+ scrollbar: true;
+ cycle: false;
+ dynamic: false;
+ border-color: var(separatorcolor);
+ border: 2px dash 0px 0px ;
+ spacing: 0;
+}
+scrollbar {
+ width: 4px ;
+ padding: 0;
+ handle-width: 8px ;
+ border: 0;
+ handle-color: var(normal-foreground);
+}
+sidebar {
+ border-color: var(separatorcolor);
+ border: 2px dash 0px 0px ;
+}
+button {
+ padding: 5px 2px ;
+ cursor: pointer;
+ spacing: 0;
+ text-color: var(normal-foreground);
+}
+button selected {
+ background-color: var(active-background);
+ text-color: var(background-color);
+}
+num-filtered-rows {
+ expand: false;
+ text-color: rgba ( 128, 128, 128, 100 % );
+}
+num-rows {
+ expand: false;
+ text-color: rgba ( 128, 128, 128, 100 % );
+}
+textbox-num-sep {
+ expand: false;
+ str: "/";
+ text-color: rgba ( 128, 128, 128, 100 % );
+}
+inputbar {
+ padding: 5px ;
+ spacing: 5px ;
+ text-color: var(normal-foreground);
+ children: [ prompt,textbox-prompt-colon,entry,num-filtered-rows,textbox-num-sep,num-rows,case-indicator ];
+}
+case-indicator {
+ spacing: 0;
+ text-color: var(normal-foreground);
+}
+entry {
+ text-color: var(normal-foreground);
+ cursor: text;
+ padding: 5px ;
+ placeholder-color: rgba ( 128, 128, 128, 100 % );
+ vertical-align: 1;
+ expand: false;
+ spacing: 0;
+ placeholder: "Type to filter";
+}
+prompt {
+ spacing: 0;
+ text-color: var(normal-foreground);
+}
+textbox-prompt-colon {
+ margin: 0px 0.3000em 0.0000em 0.0000em ;
+ expand: false;
+ str: ":";
+ text-color: inherit;
+}
diff --git a/modules/home-manager/personal/dotfiles/spacemacs.el b/modules/home-manager/personal/dotfiles/spacemacs.el
new file mode 100644
index 0000000..bd80241
--- /dev/null
+++ b/modules/home-manager/personal/dotfiles/spacemacs.el
@@ -0,0 +1,651 @@
+;; -*- mode: emacs-lisp; lexical-binding: t -*-
+;; This file is loaded by Spacemacs at startup.
+;; It must be stored in your home directory.
+
+(defun dotspacemacs/layers ()
+ "Layer configuration:
+This function should only modify configuration layer settings."
+ (setq-default
+ ;; Base distribution to use. This is a layer contained in the directory
+ ;; `+distribution'. For now available distributions are `spacemacs-base'
+ ;; or `spacemacs'. (default 'spacemacs)
+ dotspacemacs-distribution 'spacemacs
+
+ ;; Lazy installation of layers (i.e. layers are installed only when a file
+ ;; with a supported type is opened). Possible values are `all', `unused'
+ ;; and `nil'. `unused' will lazy install only unused layers (i.e. layers
+ ;; not listed in variable `dotspacemacs-configuration-layers'), `all' will
+ ;; lazy install any layer that support lazy installation even the layers
+ ;; listed in `dotspacemacs-configuration-layers'. `nil' disable the lazy
+ ;; installation feature and you have to explicitly list a layer in the
+ ;; variable `dotspacemacs-configuration-layers' to install it.
+ ;; (default 'unused)
+ dotspacemacs-enable-lazy-installation 'unused
+
+ ;; If non-nil then Spacemacs will ask for confirmation before installing
+ ;; a layer lazily. (default t)
+ dotspacemacs-ask-for-lazy-installation t
+
+ ;; List of additional paths where to look for configuration layers.
+ ;; Paths must have a trailing slash (i.e. `~/.mycontribs/')
+ dotspacemacs-configuration-layer-path '()
+
+ ;; List of configuration layers to load.
+ dotspacemacs-configuration-layers
+ '(
+ ;; ----------------------------------------------------------------
+ ;; Example of useful layers you may want to use right away.
+ ;; Uncomment some layer names and press `SPC f e R' (Vim style) or
+ ;; `M-m f e R' (Emacs style) to install them.
+ ;; ----------------------------------------------------------------
+ auto-completion
+ better-defaults
+ ;; eww
+ git
+ helm
+ multiple-cursors
+ ;; (shell :variables
+ ;; shell-default-height 30
+ ;; shell-default-position 'bottom)
+ ;; spell-checking
+ ;; syntax-checking
+ version-control
+ treemacs
+ ;; ----------------------------------------------------------------
+ ;; Programming (and markup) languages
+ ;; ----------------------------------------------------------------
+ lsp
+ csv
+ emacs-lisp spacemacs-misc
+ go
+ haskell
+ html javascript
+ latex
+ markdown
+ nixos
+ org
+ ocaml coq
+ php
+ python
+ rust
+ yaml
+ ;; ----------------------------------------------------------------
+ ;; Private layers
+ ;; ----------------------------------------------------------------
+ direnv
+ bibli-paris
+ why3
+ )
+
+ ;; List of additional packages that will be installed without being wrapped
+ ;; in a layer (generally the packages are installed only and should still be
+ ;; loaded using load/require/use-package in the user-config section below in
+ ;; this file). If you need some configuration for these packages, then
+ ;; consider creating a layer. You can also put the configuration in
+ ;; `dotspacemacs/user-config'. To use a local version of a package, use the
+ ;; `:location' property: '(your-package :location "~/path/to/your-package/")
+ ;; Also include the dependencies as they will not be resolved automatically.
+ dotspacemacs-additional-packages '(request-deferred parse-csv)
+
+ ;; A list of packages that cannot be updated.
+ dotspacemacs-frozen-packages '()
+
+ ;; A list of packages that will not be installed and loaded.
+ dotspacemacs-excluded-packages '()
+
+ ;; Defines the behaviour of Spacemacs when installing packages.
+ ;; Possible values are `used-only', `used-but-keep-unused' and `all'.
+ ;; `used-only' installs only explicitly used packages and deletes any unused
+ ;; packages as well as their unused dependencies. `used-but-keep-unused'
+ ;; installs only the used packages but won't delete unused ones. `all'
+ ;; installs *all* packages supported by Spacemacs and never uninstalls them.
+ ;; (default is `used-only')
+ dotspacemacs-install-packages 'used-but-keep-unused))
+
+(defun dotspacemacs/init ()
+ "Initialization:
+This function is called at the very beginning of Spacemacs startup,
+before layer configuration.
+It should only modify the values of Spacemacs settings."
+ ;; This setq-default sexp is an exhaustive list of all the supported
+ ;; spacemacs settings.
+ (setq-default
+ ;; If non-nil then enable support for the portable dumper. You'll need to
+ ;; compile Emacs 27 from source following the instructions in file
+ ;; EXPERIMENTAL.org at to root of the git repository.
+ ;;
+ ;; WARNING: pdumper does not work with Native Compilation, so it's disabled
+ ;; regardless of the following setting when native compilation is in effect.
+ ;;
+ ;; (default nil)
+ dotspacemacs-enable-emacs-pdumper nil
+
+ ;; Name of executable file pointing to emacs 27+. This executable must be
+ ;; in your PATH.
+ ;; (default "emacs")
+ dotspacemacs-emacs-pdumper-executable-file "emacs"
+
+ ;; Name of the Spacemacs dump file. This is the file will be created by the
+ ;; portable dumper in the cache directory under dumps sub-directory.
+ ;; To load it when starting Emacs add the parameter `--dump-file'
+ ;; when invoking Emacs 27.1 executable on the command line, for instance:
+ ;; ./emacs --dump-file=$HOME/.emacs.d/.cache/dumps/spacemacs-27.1.pdmp
+ ;; (default (format "spacemacs-%s.pdmp" emacs-version))
+ dotspacemacs-emacs-dumper-dump-file (format "spacemacs-%s.pdmp" emacs-version)
+
+ ;; If non-nil ELPA repositories are contacted via HTTPS whenever it's
+ ;; possible. Set it to nil if you have no way to use HTTPS in your
+ ;; environment, otherwise it is strongly recommended to let it set to t.
+ ;; This variable has no effect if Emacs is launched with the parameter
+ ;; `--insecure' which forces the value of this variable to nil.
+ ;; (default t)
+ dotspacemacs-elpa-https t
+
+ ;; Maximum allowed time in seconds to contact an ELPA repository.
+ ;; (default 5)
+ dotspacemacs-elpa-timeout 5
+
+ ;; Set `gc-cons-threshold' and `gc-cons-percentage' when startup finishes.
+ ;; This is an advanced option and should not be changed unless you suspect
+ ;; performance issues due to garbage collection operations.
+ ;; (default '(100000000 0.1))
+ dotspacemacs-gc-cons '(100000000 0.1)
+
+ ;; Set `read-process-output-max' when startup finishes.
+ ;; This defines how much data is read from a foreign process.
+ ;; Setting this >= 1 MB should increase performance for lsp servers
+ ;; in emacs 27.
+ ;; (default (* 1024 1024))
+ dotspacemacs-read-process-output-max (* 1024 1024)
+
+ ;; If non-nil then Spacelpa repository is the primary source to install
+ ;; a locked version of packages. If nil then Spacemacs will install the
+ ;; latest version of packages from MELPA. Spacelpa is currently in
+ ;; experimental state please use only for testing purposes.
+ ;; (default nil)
+ dotspacemacs-use-spacelpa nil
+
+ ;; If non-nil then verify the signature for downloaded Spacelpa archives.
+ ;; (default t)
+ dotspacemacs-verify-spacelpa-archives t
+
+ ;; If non-nil then spacemacs will check for updates at startup
+ ;; when the current branch is not `develop'. Note that checking for
+ ;; new versions works via git commands, thus it calls GitHub services
+ ;; whenever you start Emacs. (default nil)
+ dotspacemacs-check-for-update nil
+
+ ;; If non-nil, a form that evaluates to a package directory. For example, to
+ ;; use different package directories for different Emacs versions, set this
+ ;; to `emacs-version'. (default 'emacs-version)
+ dotspacemacs-elpa-subdirectory 'emacs-version
+
+ ;; One of `vim', `emacs' or `hybrid'.
+ ;; `hybrid' is like `vim' except that `insert state' is replaced by the
+ ;; `hybrid state' with `emacs' key bindings. The value can also be a list
+ ;; with `:variables' keyword (similar to layers). Check the editing styles
+ ;; section of the documentation for details on available variables.
+ ;; (default 'vim)
+ dotspacemacs-editing-style 'vim
+
+ ;; If non-nil show the version string in the Spacemacs buffer. It will
+ ;; appear as (spacemacs version)@(emacs version)
+ ;; (default t)
+ dotspacemacs-startup-buffer-show-version t
+
+ ;; Specify the startup banner. Default value is `official', it displays
+ ;; the official spacemacs logo. An integer value is the index of text
+ ;; banner, `random' chooses a random text banner in `core/banners'
+ ;; directory. A string value must be a path to an image format supported
+ ;; by your Emacs build.
+ ;; If the value is nil then no banner is displayed. (default 'official)
+ dotspacemacs-startup-banner 'official
+
+ ;; Scale factor controls the scaling (size) of the startup banner. Default
+ ;; value is `auto' for scaling the logo automatically to fit all buffer
+ ;; contents, to a maximum of the full image height and a minimum of 3 line
+ ;; heights. If set to a number (int or float) it is used as a constant
+ ;; scaling factor for the default logo size.
+ dotspacemacs-startup-banner-scale 'auto
+
+ ;; List of items to show in startup buffer or an association list of
+ ;; the form `(list-type . list-size)`. If nil then it is disabled.
+ ;; Possible values for list-type are:
+ ;; `recents' `recents-by-project' `bookmarks' `projects' `agenda' `todos'.
+ ;; List sizes may be nil, in which case
+ ;; `spacemacs-buffer-startup-lists-length' takes effect.
+ ;; The exceptional case is `recents-by-project', where list-type must be a
+ ;; pair of numbers, e.g. `(recents-by-project . (7 . 5))', where the first
+ ;; number is the project limit and the second the limit on the recent files
+ ;; within a project.
+ dotspacemacs-startup-lists '((recents . 5)
+ (projects . 7))
+
+ ;; True if the home buffer should respond to resize events. (default t)
+ dotspacemacs-startup-buffer-responsive t
+
+ ;; Show numbers before the startup list lines. (default t)
+ dotspacemacs-show-startup-list-numbers t
+
+ ;; The minimum delay in seconds between number key presses. (default 0.4)
+ dotspacemacs-startup-buffer-multi-digit-delay 0.4
+
+ ;; If non-nil, show file icons for entries and headings on Spacemacs home buffer.
+ ;; This has no effect in terminal or if "all-the-icons" package or the font
+ ;; is not installed. (default nil)
+ dotspacemacs-startup-buffer-show-icons nil
+
+ ;; Default major mode for a new empty buffer. Possible values are mode
+ ;; names such as `text-mode'; and `nil' to use Fundamental mode.
+ ;; (default `text-mode')
+ dotspacemacs-new-empty-buffer-major-mode 'text-mode
+
+ ;; Default major mode of the scratch buffer (default `text-mode')
+ dotspacemacs-scratch-mode 'text-mode
+
+ ;; If non-nil, *scratch* buffer will be persistent. Things you write down in
+ ;; *scratch* buffer will be saved and restored automatically.
+ dotspacemacs-scratch-buffer-persistent nil
+
+ ;; If non-nil, `kill-buffer' on *scratch* buffer
+ ;; will bury it instead of killing.
+ dotspacemacs-scratch-buffer-unkillable nil
+
+ ;; Initial message in the scratch buffer, such as "Welcome to Spacemacs!"
+ ;; (default nil)
+ dotspacemacs-initial-scratch-message nil
+
+ ;; List of themes, the first of the list is loaded when spacemacs starts.
+ ;; Press `SPC T n' to cycle to the next theme in the list (works great
+ ;; with 2 themes variants, one dark and one light)
+ dotspacemacs-themes '(spacemacs-dark
+ spacemacs-light)
+
+ ;; Set the theme for the Spaceline. Supported themes are `spacemacs',
+ ;; `all-the-icons', `custom', `doom', `vim-powerline' and `vanilla'. The
+ ;; first three are spaceline themes. `doom' is the doom-emacs mode-line.
+ ;; `vanilla' is default Emacs mode-line. `custom' is a user defined themes,
+ ;; refer to the DOCUMENTATION.org for more info on how to create your own
+ ;; spaceline theme. Value can be a symbol or list with additional properties.
+ ;; (default '(spacemacs :separator wave :separator-scale 1.5))
+ dotspacemacs-mode-line-theme '(spacemacs :separator wave :separator-scale 1.5)
+
+ ;; If non-nil the cursor color matches the state color in GUI Emacs.
+ ;; (default t)
+ dotspacemacs-colorize-cursor-according-to-state t
+
+ ;; Default font or prioritized list of fonts. The `:size' can be specified as
+ ;; a non-negative integer (pixel size), or a floating-point (point size).
+ ;; Point size is recommended, because it's device independent. (default 10.0)
+ dotspacemacs-default-font '("Source Code Pro"
+ :size 14.0
+ :weight normal
+ :width normal)
+
+ ;; The leader key (default "SPC")
+ dotspacemacs-leader-key "SPC"
+
+ ;; The key used for Emacs commands `M-x' (after pressing on the leader key).
+ ;; (default "SPC")
+ dotspacemacs-emacs-command-key "SPC"
+
+ ;; The key used for Vim Ex commands (default ":")
+ dotspacemacs-ex-command-key ":"
+
+ ;; The leader key accessible in `emacs state' and `insert state'
+ ;; (default "M-m")
+ dotspacemacs-emacs-leader-key "M-m"
+
+ ;; Major mode leader key is a shortcut key which is the equivalent of
+ ;; pressing `<leader> m`. Set it to `nil` to disable it. (default ",")
+ dotspacemacs-major-mode-leader-key ","
+
+ ;; Major mode leader key accessible in `emacs state' and `insert state'.
+ ;; (default "C-M-m" for terminal mode, "<M-return>" for GUI mode).
+ ;; Thus M-RET should work as leader key in both GUI and terminal modes.
+ ;; C-M-m also should work in terminal mode, but not in GUI mode.
+ dotspacemacs-major-mode-emacs-leader-key (if window-system "<M-return>" "C-M-m")
+
+ ;; These variables control whether separate commands are bound in the GUI to
+ ;; the key pairs `C-i', `TAB' and `C-m', `RET'.
+ ;; Setting it to a non-nil value, allows for separate commands under `C-i'
+ ;; and TAB or `C-m' and `RET'.
+ ;; In the terminal, these pairs are generally indistinguishable, so this only
+ ;; works in the GUI. (default nil)
+ dotspacemacs-distinguish-gui-tab nil
+
+ ;; Name of the default layout (default "Default")
+ dotspacemacs-default-layout-name "Default"
+
+ ;; If non-nil the default layout name is displayed in the mode-line.
+ ;; (default nil)
+ dotspacemacs-display-default-layout nil
+
+ ;; If non-nil then the last auto saved layouts are resumed automatically upon
+ ;; start. (default nil)
+ dotspacemacs-auto-resume-layouts nil
+
+ ;; If non-nil, auto-generate layout name when creating new layouts. Only has
+ ;; effect when using the "jump to layout by number" commands. (default nil)
+ dotspacemacs-auto-generate-layout-names nil
+
+ ;; Size (in MB) above which spacemacs will prompt to open the large file
+ ;; literally to avoid performance issues. Opening a file literally means that
+ ;; no major mode or minor modes are active. (default is 1)
+ dotspacemacs-large-file-size 1
+
+ ;; Location where to auto-save files. Possible values are `original' to
+ ;; auto-save the file in-place, `cache' to auto-save the file to another
+ ;; file stored in the cache directory and `nil' to disable auto-saving.
+ ;; (default 'cache)
+ dotspacemacs-auto-save-file-location 'cache
+
+ ;; Maximum number of rollback slots to keep in the cache. (default 5)
+ dotspacemacs-max-rollback-slots 5
+
+ ;; If non-nil, the paste transient-state is enabled. While enabled, after you
+ ;; paste something, pressing `C-j' and `C-k' several times cycles through the
+ ;; elements in the `kill-ring'. (default nil)
+ dotspacemacs-enable-paste-transient-state nil
+
+ ;; Which-key delay in seconds. The which-key buffer is the popup listing
+ ;; the commands bound to the current keystroke sequence. (default 0.4)
+ dotspacemacs-which-key-delay 0.4
+
+ ;; Which-key frame position. Possible values are `right', `bottom' and
+ ;; `right-then-bottom'. right-then-bottom tries to display the frame to the
+ ;; right; if there is insufficient space it displays it at the bottom.
+ ;; (default 'bottom)
+ dotspacemacs-which-key-position 'bottom
+
+ ;; Control where `switch-to-buffer' displays the buffer. If nil,
+ ;; `switch-to-buffer' displays the buffer in the current window even if
+ ;; another same-purpose window is available. If non-nil, `switch-to-buffer'
+ ;; displays the buffer in a same-purpose window even if the buffer can be
+ ;; displayed in the current window. (default nil)
+ dotspacemacs-switch-to-buffer-prefers-purpose nil
+
+ ;; If non-nil a progress bar is displayed when spacemacs is loading. This
+ ;; may increase the boot time on some systems and emacs builds, set it to
+ ;; nil to boost the loading time. (default t)
+ dotspacemacs-loading-progress-bar t
+
+ ;; If non-nil the frame is fullscreen when Emacs starts up. (default nil)
+ ;; (Emacs 24.4+ only)
+ dotspacemacs-fullscreen-at-startup nil
+
+ ;; If non-nil `spacemacs/toggle-fullscreen' will not use native fullscreen.
+ ;; Use to disable fullscreen animations in OSX. (default nil)
+ dotspacemacs-fullscreen-use-non-native nil
+
+ ;; If non-nil the frame is maximized when Emacs starts up.
+ ;; Takes effect only if `dotspacemacs-fullscreen-at-startup' is nil.
+ ;; (default nil) (Emacs 24.4+ only)
+ dotspacemacs-maximized-at-startup nil
+
+ ;; If non-nil the frame is undecorated when Emacs starts up. Combine this
+ ;; variable with `dotspacemacs-maximized-at-startup' to obtain fullscreen
+ ;; without external boxes. Also disables the internal border. (default nil)
+ dotspacemacs-undecorated-at-startup nil
+
+ ;; A value from the range (0..100), in increasing opacity, which describes
+ ;; the transparency level of a frame when it's active or selected.
+ ;; Transparency can be toggled through `toggle-transparency'. (default 90)
+ dotspacemacs-active-transparency 90
+
+ ;; A value from the range (0..100), in increasing opacity, which describes
+ ;; the transparency level of a frame when it's inactive or deselected.
+ ;; Transparency can be toggled through `toggle-transparency'. (default 90)
+ dotspacemacs-inactive-transparency 90
+
+ ;; A value from the range (0..100), in increasing opacity, which describes the
+ ;; transparency level of a frame background when it's active or selected. Transparency
+ ;; can be toggled through `toggle-background-transparency'. (default 90)
+ dotspacemacs-background-transparency 90
+
+ ;; If non-nil show the titles of transient states. (default t)
+ dotspacemacs-show-transient-state-title t
+
+ ;; If non-nil show the color guide hint for transient state keys. (default t)
+ dotspacemacs-show-transient-state-color-guide t
+
+ ;; If non-nil unicode symbols are displayed in the mode line.
+ ;; If you use Emacs as a daemon and wants unicode characters only in GUI set
+ ;; the value to quoted `display-graphic-p'. (default t)
+ dotspacemacs-mode-line-unicode-symbols t
+
+ ;; If non-nil smooth scrolling (native-scrolling) is enabled. Smooth
+ ;; scrolling overrides the default behavior of Emacs which recenters point
+ ;; when it reaches the top or bottom of the screen. (default t)
+ dotspacemacs-smooth-scrolling t
+
+ ;; Show the scroll bar while scrolling. The auto hide time can be configured
+ ;; by setting this variable to a number. (default t)
+ dotspacemacs-scroll-bar-while-scrolling t
+
+ ;; Control line numbers activation.
+ ;; If set to `t', `relative' or `visual' then line numbers are enabled in all
+ ;; `prog-mode' and `text-mode' derivatives. If set to `relative', line
+ ;; numbers are relative. If set to `visual', line numbers are also relative,
+ ;; but only visual lines are counted. For example, folded lines will not be
+ ;; counted and wrapped lines are counted as multiple lines.
+ ;; This variable can also be set to a property list for finer control:
+ ;; '(:relative nil
+ ;; :visual nil
+ ;; :disabled-for-modes dired-mode
+ ;; doc-view-mode
+ ;; markdown-mode
+ ;; org-mode
+ ;; pdf-view-mode
+ ;; text-mode
+ ;; :size-limit-kb 1000)
+ ;; When used in a plist, `visual' takes precedence over `relative'.
+ ;; (default nil)
+ dotspacemacs-line-numbers nil
+
+ ;; Code folding method. Possible values are `evil', `origami' and `vimish'.
+ ;; (default 'evil)
+ dotspacemacs-folding-method 'evil
+
+ ;; If non-nil and `dotspacemacs-activate-smartparens-mode' is also non-nil,
+ ;; `smartparens-strict-mode' will be enabled in programming modes.
+ ;; (default nil)
+ dotspacemacs-smartparens-strict-mode nil
+
+ ;; If non-nil smartparens-mode will be enabled in programming modes.
+ ;; (default t)
+ dotspacemacs-activate-smartparens-mode t
+
+ ;; If non-nil pressing the closing parenthesis `)' key in insert mode passes
+ ;; over any automatically added closing parenthesis, bracket, quote, etc...
+ ;; This can be temporary disabled by pressing `C-q' before `)'. (default nil)
+ dotspacemacs-smart-closing-parenthesis nil
+
+ ;; Select a scope to highlight delimiters. Possible values are `any',
+ ;; `current', `all' or `nil'. Default is `all' (highlight any scope and
+ ;; emphasis the current one). (default 'all)
+ dotspacemacs-highlight-delimiters 'all
+
+ ;; If non-nil, start an Emacs server if one is not already running.
+ ;; (default nil)
+ dotspacemacs-enable-server nil
+
+ ;; Set the emacs server socket location.
+ ;; If nil, uses whatever the Emacs default is, otherwise a directory path
+ ;; like \"~/.emacs.d/server\". It has no effect if
+ ;; `dotspacemacs-enable-server' is nil.
+ ;; (default nil)
+ dotspacemacs-server-socket-dir nil
+
+ ;; If non-nil, advise quit functions to keep server open when quitting.
+ ;; (default nil)
+ dotspacemacs-persistent-server nil
+
+ ;; List of search tool executable names. Spacemacs uses the first installed
+ ;; tool of the list. Supported tools are `rg', `ag', `pt', `ack' and `grep'.
+ ;; (default '("rg" "ag" "pt" "ack" "grep"))
+ dotspacemacs-search-tools '("rg" "ag" "pt" "ack" "grep")
+
+ ;; Format specification for setting the frame title.
+ ;; %a - the `abbreviated-file-name', or `buffer-name'
+ ;; %t - `projectile-project-name'
+ ;; %I - `invocation-name'
+ ;; %S - `system-name'
+ ;; %U - contents of $USER
+ ;; %b - buffer name
+ ;; %f - visited file name
+ ;; %F - frame name
+ ;; %s - process status
+ ;; %p - percent of buffer above top of window, or Top, Bot or All
+ ;; %P - percent of buffer above bottom of window, perhaps plus Top, or Bot or All
+ ;; %m - mode name
+ ;; %n - Narrow if appropriate
+ ;; %z - mnemonics of buffer, terminal, and keyboard coding systems
+ ;; %Z - like %z, but including the end-of-line format
+ ;; If nil then Spacemacs uses default `frame-title-format' to avoid
+ ;; performance issues, instead of calculating the frame title by
+ ;; `spacemacs/title-prepare' all the time.
+ ;; (default "%I@%S")
+ dotspacemacs-frame-title-format "%I@%S"
+
+ ;; Format specification for setting the icon title format
+ ;; (default nil - same as frame-title-format)
+ dotspacemacs-icon-title-format nil
+
+ ;; Color highlight trailing whitespace in all prog-mode and text-mode derived
+ ;; modes such as c++-mode, python-mode, emacs-lisp, html-mode, rst-mode etc.
+ ;; (default t)
+ dotspacemacs-show-trailing-whitespace t
+
+ ;; Delete whitespace while saving buffer. Possible values are `all'
+ ;; to aggressively delete empty line and long sequences of whitespace,
+ ;; `trailing' to delete only the whitespace at end of lines, `changed' to
+ ;; delete only whitespace for changed lines or `nil' to disable cleanup.
+ ;; (default nil)
+ dotspacemacs-whitespace-cleanup nil
+
+ ;; If non-nil activate `clean-aindent-mode' which tries to correct
+ ;; virtual indentation of simple modes. This can interfere with mode specific
+ ;; indent handling like has been reported for `go-mode'.
+ ;; If it does deactivate it here.
+ ;; (default t)
+ dotspacemacs-use-clean-aindent-mode t
+
+ ;; Accept SPC as y for prompts if non-nil. (default nil)
+ dotspacemacs-use-SPC-as-y nil
+
+ ;; If non-nil shift your number row to match the entered keyboard layout
+ ;; (only in insert state). Currently supported keyboard layouts are:
+ ;; `qwerty-us', `qwertz-de' and `querty-ca-fr'.
+ ;; New layouts can be added in `spacemacs-editing' layer.
+ ;; (default nil)
+ dotspacemacs-swap-number-row nil
+
+ ;; Either nil or a number of seconds. If non-nil zone out after the specified
+ ;; number of seconds. (default nil)
+ dotspacemacs-zone-out-when-idle nil
+
+ ;; Run `spacemacs/prettify-org-buffer' when
+ ;; visiting README.org files of Spacemacs.
+ ;; (default nil)
+ dotspacemacs-pretty-docs nil
+
+ ;; If nil the home buffer shows the full path of agenda items
+ ;; and todos. If non-nil only the file name is shown.
+ dotspacemacs-home-shorten-agenda-source nil
+
+ ;; If non-nil then byte-compile some of Spacemacs files.
+ dotspacemacs-byte-compile nil))
+
+(defun dotspacemacs/user-env ()
+ "Environment variables setup.
+This function defines the environment variables for your Emacs session. By
+default it calls `spacemacs/load-spacemacs-env' which loads the environment
+variables declared in `~/.spacemacs.env' or `~/.spacemacs.d/.spacemacs.env'.
+See the header of this file for more information."
+ (spacemacs/load-spacemacs-env)
+)
+
+(defun dotspacemacs/user-init ()
+ "Initialization for user code:
+This function is called immediately after `dotspacemacs/init', before layer
+configuration.
+It is mostly for variables that should be set before packages are loaded.
+If you are unsure, try setting them in `dotspacemacs/user-config' first."
+)
+
+
+(defun dotspacemacs/user-load ()
+ "Library to load while dumping.
+This function is called only while dumping Spacemacs configuration. You can
+`require' or `load' the libraries of your choice that will be included in the
+dump."
+)
+
+
+(defun dotspacemacs/user-config ()
+ "Configuration for user code:
+This function is called at the very end of Spacemacs startup, after layer
+configuration.
+Put your configuration code here, except for variables that should be set
+before packages are loaded."
+ ;; Variables customization
+ (custom-set-variables
+ '(merlin-command "ocamlmerlin")
+
+ ;; reftex
+ ;; https://tex.stackexchange.com/a/54825
+ '(reftex-bibliography-commands '("bibliography"
+ "nobibliography"
+ "addbibresource"))
+ ;; https://tex.stackexchange.com/a/213909
+ '(reftex-use-external-file-finders t)
+
+ ;; don't pop warning buffer on native comp
+ '(native-comp-async-report-warnings-errors 'silent)
+
+ ;; restrict which warnings are shown
+ '(warning-minimum-level :emergency)
+ )
+
+ ;; auto-completion
+ (global-company-mode t)
+
+ ;; hooks
+ (add-hook 'LaTeX-mode-hook 'outline-minor-mode)
+
+ ;; Key bindings
+ (defun my-ediff-dotfile-and-template ()
+ (interactive)
+ (ediff-files "~/code/nix/latitude-7490/home/config/dotfiles/spacemacs"
+ (concat dotspacemacs-template-directory ".spacemacs.template")))
+ (spacemacs/set-leader-keys "feD" 'my-ediff-dotfile-and-template)
+ (defun my-open-dotfile ()
+ (interactive)
+ (find-file "~/code/nix/latitude-7490/home/config/dotfiles/spacemacs"))
+ (spacemacs/set-leader-keys "fed" 'my-open-dotfile)
+
+ (spacemacs/set-leader-keys-for-major-mode 'magit-mode "b" 'magit-branch)
+)
+
+;; Do not write anything past this comment. This is where Emacs will
+;; auto-generate custom variable definitions.
+(defun dotspacemacs/emacs-custom-settings ()
+ "Emacs custom settings.
+This is an auto-generated function, do not modify its content directly, use
+Emacs customize menu instead.
+This function is called at the very end of Spacemacs initialization."
+(custom-set-variables
+ ;; custom-set-variables was added by Custom.
+ ;; If you edit it by hand, you could mess it up, so be careful.
+ ;; Your init file should contain only one such instance.
+ ;; If there is more than one, they won't work right.
+ '(package-selected-packages
+ '(yapfify utop tuareg caml sphinx-doc pytest pyenv-mode py-isort poetry pippel pipenv pyvenv pip-requirements ocp-indent ocamlformat merlin-eldoc live-py-mode importmagic epc ctable concurrent deferred helm-pydoc flycheck-ocaml merlin dune cython-mode company-reftex company-math math-symbol-lists company-auctex company-anaconda blacken auctex anaconda-mode pythonic yasnippet-snippets unfill treemacs-magit smeargle orgit-forge orgit org-rich-yank org-projectile org-category-capture org-present org-pomodoro alert log4e gntp org-mime org-download org-cliplink org-brain nix-mode mwim mmm-mode markdown-toc magit-svn magit-section magit-gitflow magit-popup htmlize helm-org-rifle helm-nixos-options helm-gitignore helm-git-grep helm-company helm-c-yasnippet gnuplot gitignore-templates gitignore-mode gitconfig-mode gitattributes-mode git-timemachine git-messenger git-link git-gutter-fringe+ fringe-helper git-gutter+ gh-md fuzzy forge markdown-mode magit ghub closql emacsql-sqlite emacsql treepy git-commit with-editor transient flyspell-correct-helm flyspell-correct flycheck-pos-tip pos-tip evil-org company-nixos-options nixos-options company browse-at-remote auto-yasnippet yasnippet auto-dictionary ac-ispell auto-complete ws-butler writeroom-mode visual-fill-column winum volatile-highlights vi-tilde-fringe uuidgen undo-tree treemacs-projectile treemacs-persp treemacs-icons-dired treemacs-evil treemacs cfrs ht pfuture posframe toc-org symon symbol-overlay string-inflection string-edit spaceline-all-the-icons memoize all-the-icons spaceline powerline restart-emacs request rainbow-delimiters popwin persp-mode password-generator paradox spinner overseer org-superstar open-junk-file nameless multi-line shut-up macrostep lorem-ipsum link-hint indent-guide hungry-delete hl-todo highlight-parentheses highlight-numbers parent-mode highlight-indentation helm-xref helm-themes helm-swoop helm-purpose window-purpose imenu-list helm-projectile helm-org helm-mode-manager helm-make helm-ls-git helm-flx helm-descbinds helm-ag google-translate golden-ratio flycheck-package package-lint flycheck flycheck-elsa flx-ido flx fancy-battery eyebrowse expand-region evil-visualstar evil-visual-mark-mode evil-unimpaired f evil-tutor evil-textobj-line evil-surround evil-numbers evil-nerd-commenter evil-mc evil-matchit evil-lisp-state evil-lion evil-indent-plus evil-iedit-state evil-goggles evil-exchange evil-escape evil-ediff evil-easymotion evil-collection annalist evil-cleverparens smartparens evil-args evil-anzu anzu eval-sexp-fu emr iedit clang-format projectile paredit list-utils pkg-info epl elisp-slime-nav editorconfig dumb-jump s drag-stuff dired-quick-sort devdocs define-word dash column-enforce-mode clean-aindent-mode centered-cursor-mode auto-highlight-symbol auto-compile packed aggressive-indent ace-window ace-link ace-jump-helm-line helm avy helm-core popup which-key use-package pcre2el org-plus-contrib hydra lv hybrid-mode font-lock+ evil goto-chg dotenv-mode diminish bind-map bind-key async)))
+(custom-set-faces
+ ;; custom-set-faces was added by Custom.
+ ;; If you edit it by hand, you could mess it up, so be careful.
+ ;; Your init file should contain only one such instance.
+ ;; If there is more than one, they won't work right.
+ )
+)
diff --git a/modules/home-manager/personal/dotfiles/venv-manager.nix b/modules/home-manager/personal/dotfiles/venv-manager.nix
new file mode 100644
index 0000000..248cb0c
--- /dev/null
+++ b/modules/home-manager/personal/dotfiles/venv-manager.nix
@@ -0,0 +1,39 @@
+{ config, lib, pkgs, ... }:
+
+{
+ direnv.enable = lib.mkDefault true;
+
+ haskell = { spacemacs.enable = lib.mkDefault true; };
+
+ latex = {
+ packages = tl: {
+ inherit (tl)
+ scheme-basic # scheme
+ koma-script ragged2e everysel footmisc # koma
+ ;
+ };
+ latexmk = {
+ enable = lib.mkDefault true;
+ output.pdf.enable = lib.mkDefault true;
+ rc =
+ lib.optional (lib.pathExists ~/.config/latexmkrc) ~/.config/latexmkrc;
+ };
+ };
+
+ nix.enable = lib.mkDefault true;
+
+ ocaml.tuareg.enable = lib.mkDefault true;
+
+ coq.coq = pkgs.coq_8_15;
+ # pkgs.coq_8_15.override { buildIde = false; };
+
+ why3 = {
+ defaultEditor = "emacsclient -c";
+ extraConfig = lib.optionalString config.coq.enable ''
+ [prover]
+ editor = ""
+ name = "Coq"
+ version = "8.15+rc1"
+ '';
+ };
+}
diff --git a/modules/home-manager/personal/environment.nix b/modules/home-manager/personal/environment.nix
new file mode 100644
index 0000000..3d29db1
--- /dev/null
+++ b/modules/home-manager/personal/environment.nix
@@ -0,0 +1,20 @@
+{ config, lib, pkgs, ... }:
+
+{
+ home.packages = with pkgs; [ coreutils moreutils ];
+ personal.home.wallpaper = lib.mkDefault config.personal.home.dotfiles.wallpaper;
+
+ programs.bash = {
+ enable = lib.mkDefault true;
+ };
+
+ home = {
+ shellAliases = {
+ amimullvad = "curl -Ls https://am.i.mullvad.net/connected";
+ rm = "rm -f";
+ ssh = "TERM=xterm-256color ssh";
+ edit = "$EDITOR";
+ };
+ sessionVariables = { CDPATH = "~"; };
+ };
+}
diff --git a/modules/home-manager/personal/gui/default.nix b/modules/home-manager/personal/gui/default.nix
new file mode 100644
index 0000000..fe50f0c
--- /dev/null
+++ b/modules/home-manager/personal/gui/default.nix
@@ -0,0 +1,42 @@
+{ config, lib, pkgs, ... }@extraArgs:
+
+let cfg = config.personal.gui;
+in {
+ imports = [ ./redshift.nix ./x ];
+
+ options.personal.gui = {
+ enable = lib.mkEnableOption "GUI" // {
+ default = extraArgs.osConfig.personal.gui.enable or false;
+ };
+ };
+
+ config = lib.mkIf cfg.enable {
+ services.kdeconnect.indicator = lib.mkDefault true;
+
+ home.pointerCursor = lib.mkDefault {
+ name = "Numix-Cursor-Light";
+ package = pkgs.numix-cursor-theme;
+ };
+
+ dconf.enable = lib.mkDefault true;
+ gtk = {
+ enable = lib.mkDefault true;
+ theme = lib.mkDefault {
+ name = "Arc-Dark";
+ package = pkgs.arc-theme;
+ };
+ iconTheme = lib.mkDefault {
+ name = "breeze-dark";
+ package = pkgs.breeze-icons;
+ };
+ };
+ qt = {
+ enable = lib.mkDefault true;
+ platformTheme = lib.mkDefault "gtk";
+ };
+
+ home.packages = lib.optional config.dconf.enable pkgs.dconf
+ ++ [ pkgs.keepassxc ];
+ programs.firefox.enable = true;
+ };
+}
diff --git a/modules/home-manager/personal/gui/redshift.nix b/modules/home-manager/personal/gui/redshift.nix
new file mode 100644
index 0000000..2242ad2
--- /dev/null
+++ b/modules/home-manager/personal/gui/redshift.nix
@@ -0,0 +1,17 @@
+{ config, lib, ... }@extraArgs:
+
+{
+ services.redshift = {
+ enable = lib.mkDefault config.personal.gui.enable;
+ tray = lib.mkDefault true;
+ temperature = {
+ day = lib.mkDefault 2500;
+ night = lib.mkDefault 2500;
+ };
+ latitude =
+ extraArgs.osConfig.location.latitude or (lib.mkDefault "48.856614");
+ longitude =
+ extraArgs.osConfig.location.longitude or (lib.mkDefault "2.3522219");
+ settings.redshift.transition = lib.mkDefault 0;
+ };
+}
diff --git a/modules/home-manager/personal/gui/x/default.nix b/modules/home-manager/personal/gui/x/default.nix
new file mode 100644
index 0000000..0de1552
--- /dev/null
+++ b/modules/home-manager/personal/gui/x/default.nix
@@ -0,0 +1,14 @@
+{ config, lib, ... }@extraArgs:
+
+let cfg = config.personal.x;
+in {
+ imports = [ ./i3 ./idlehook.nix ];
+
+ options.personal.x = {
+ enable = lib.mkEnableOption "X" // {
+ default = extraArgs.osConfig.services.xserver.enable or false;
+ };
+ };
+
+ config.xsession.enable = lib.mkDefault cfg.enable;
+}
diff --git a/modules/home-manager/personal/gui/x/i3/bar/default.nix b/modules/home-manager/personal/gui/x/i3/bar/default.nix
new file mode 100644
index 0000000..58d4bce
--- /dev/null
+++ b/modules/home-manager/personal/gui/x/i3/bar/default.nix
@@ -0,0 +1,27 @@
+{ config, lib, pkgs, ... }@extraArgs:
+
+let
+ statusPackage =
+ pkgs.personal.barista.override { i3statusGo = ./i3status.go; };
+in {
+ xsession.windowManager.i3.config.bars = [{
+ statusCommand = "${statusPackage}/bin/i3status";
+ fonts = {
+ names = [ "roboto" ];
+ size = 11.0;
+ };
+ colors.background = "#111111";
+ }];
+
+ home.packages = with pkgs;
+ lib.optionals
+ (config.xsession.enable && config.xsession.windowManager.i3.enable) [
+ material-design-icons
+ roboto
+ # source-code-pro
+ ];
+
+ # (Miscellaneous) Tray icons
+ services.blueman-applet.enable =
+ lib.mkDefault (extraArgs.osConfig.services.blueman.enable);
+}
diff --git a/modules/home-manager/personal/gui/x/i3/bar/i3status.go b/modules/home-manager/personal/gui/x/i3/bar/i3status.go
new file mode 100644
index 0000000..196e6cc
--- /dev/null
+++ b/modules/home-manager/personal/gui/x/i3/bar/i3status.go
@@ -0,0 +1,289 @@
+package main
+
+import (
+ "io"
+ "net/http"
+ "os"
+ "regexp"
+ "strconv"
+ "time"
+
+ "barista.run"
+ "barista.run/bar"
+ "barista.run/colors"
+ "barista.run/group"
+ "barista.run/modules/battery"
+ "barista.run/modules/clock"
+ "barista.run/modules/diskspace"
+ "barista.run/modules/funcs"
+ "barista.run/modules/netinfo"
+ "barista.run/modules/systemd"
+ "barista.run/modules/volume"
+ "barista.run/modules/volume/pulseaudio"
+ "barista.run/modules/wlan"
+ "barista.run/outputs"
+ "barista.run/pango"
+ "barista.run/pango/icons/mdi"
+)
+
+func main() {
+ // Constants
+ colors.LoadFromMap(map[string]string{
+ // Color palette of Cezanne's Vue de la Baie de Marseille
+ "good": "#C5D294",
+ "degraded": "#E9CC67",
+ "bad": "#FFBC88",
+ })
+ mdi.Load() // repo path will be inserted at build time
+
+ // Display status of several services
+ updateSuccessIcon := pango.Icon("mdi-reload")
+ updatingIcon := pango.Icon("mdi-update")
+ updateFailIcon := pango.Icon("mdi-reload-alert")
+ garbageFullIcon := pango.Icon("mdi-delete")
+ garbageEmptyingIcon := pango.Icon("mdi-delete-restore")
+ garbageEmptyIcon := pango.Icon("mdi-delete-outline")
+ barista.Add(group.Simple(systemd.Service("nixos-upgrade").Output(func(i systemd.ServiceInfo) bar.Output {
+ state := i.UnitInfo.State
+ var colorScheme string
+ var output *pango.Node
+ switch {
+ case state == systemd.StateInactive:
+ colorScheme = "good"
+ output = updateSuccessIcon
+ case state == systemd.StateActivating:
+ colorScheme = "degraded"
+ output = updatingIcon
+ default:
+ colorScheme = "bad"
+ output = updateFailIcon
+ }
+ return outputs.Pango(output).Color(colors.Scheme(colorScheme))
+ }),
+ systemd.Service("nix-gc").Output(func(i systemd.ServiceInfo) bar.Output {
+ state := i.UnitInfo.State
+ var colorScheme string
+ var output *pango.Node
+ switch {
+ case state == systemd.StateInactive:
+ colorScheme = "good"
+ output = garbageEmptyIcon
+ case state == systemd.StateActivating:
+ colorScheme = "degraded"
+ output = garbageEmptyingIcon
+ default:
+ colorScheme = "bad"
+ output = garbageFullIcon
+ }
+ return outputs.Pango(output).Color(colors.Scheme(colorScheme))
+ })))
+
+ // Display space left on /
+ storageIcon := pango.Icon("mdi-database")
+ barista.Add(diskspace.New("/").Output(func(i diskspace.Info) bar.Output {
+ used := i.UsedPct()
+ var colorScheme string
+ if used >= 90 {
+ colorScheme = "bad"
+ } else if used >= 50 {
+ colorScheme = "degraded"
+ } else {
+ colorScheme = "good"
+ }
+ return outputs.Pango(storageIcon, pango.Textf(" %d%%", used)).Color(colors.Scheme(colorScheme))
+ }))
+
+ // Check connection to the Mullvad VPN
+ mullvadIsUpRe := regexp.MustCompile(`^You are connected to Mullvad`)
+ mullvadServerRe := regexp.MustCompile(`\(server (.*)\)`)
+ mullvadIpRe := regexp.MustCompile(`Your IP address is (.*)`)
+ client := &http.Client{Timeout: 3 * time.Second}
+ incognitoIcon := pango.Icon("mdi-incognito")
+ incognitoOffIcon := pango.Icon("mdi-incognito-off")
+ barista.Add(funcs.Every(5*time.Second, func(s bar.Sink) {
+ icon := incognitoOffIcon
+ message := pango.Text("")
+ colorScheme := "bad"
+ res, err := client.Get("https://am.i.mullvad.net/connected")
+ if !s.Error(err) {
+ status, err := io.ReadAll(res.Body)
+ res.Body.Close()
+ if !s.Error(err) {
+ var re *regexp.Regexp
+ if mullvadIsUpRe.Match(status) {
+ re = mullvadServerRe
+ colorScheme = "good"
+ icon = incognitoIcon
+ } else {
+ re = mullvadIpRe
+ colorScheme = "degraded"
+ }
+ result := re.FindSubmatch(status)
+ if len(result) >= 2 {
+ message = pango.Textf(" %s", result[1])
+ }
+ }
+ }
+ client.CloseIdleConnections()
+ s.Output(outputs.Pango(icon, message).Color(colors.Scheme(colorScheme)))
+ }))
+
+ // Display the wifi status
+ wifiOffIcon := pango.Icon("mdi-wifi-off")
+ wifiRefreshIcon := pango.Icon("mdi-wifi-refresh")
+ wifiOnIcon := pango.Icon("mdi-wifi")
+ barista.Add(wlan.Named("wlp2s0").Output(func(w wlan.Info) bar.Output {
+ var output *pango.Node
+ var colorScheme string
+ switch {
+ case w.Connected():
+ output = pango.New(wifiOnIcon, pango.Textf(" %s", w.SSID))
+ colorScheme = "good"
+ case w.Connecting():
+ output = wifiRefreshIcon
+ colorScheme = "degraded"
+ default:
+ output = wifiOffIcon
+ colorScheme = "bad"
+ }
+ return outputs.Pango(output).Color(colors.Scheme(colorScheme))
+ }))
+
+ // Display the ethernet status
+ ethernetCableOnIcon := pango.Icon("mdi-ethernet-cable")
+ ethernetCableOffIcon := pango.Icon("mdi-ethernet-cable-off")
+ barista.Add(netinfo.Prefix("e").Output(func(s netinfo.State) bar.Output {
+ var output *pango.Node
+ var colorScheme string
+ switch {
+ case s.Connected():
+ ip := "<no ip>"
+ if len(s.IPs) > 0 {
+ ip = s.IPs[0].String()
+ }
+ output = pango.New(ethernetCableOnIcon, pango.Textf(" %s", ip))
+ colorScheme = "good"
+ case s.Connecting():
+ output = ethernetCableOnIcon
+ colorScheme = "degraded"
+ default:
+ output = ethernetCableOffIcon
+ colorScheme = "bad"
+ }
+ return outputs.Pango(output).Color(colors.Scheme(colorScheme))
+ }))
+
+ // Display the battery status
+ batteryIcons := [11]*pango.Node{pango.Icon("mdi-battery-outline"),
+ pango.Icon("mdi-battery-10"),
+ pango.Icon("mdi-battery-20"),
+ pango.Icon("mdi-battery-30"),
+ pango.Icon("mdi-battery-40"),
+ pango.Icon("mdi-battery-50"),
+ pango.Icon("mdi-battery-60"),
+ pango.Icon("mdi-battery-70"),
+ pango.Icon("mdi-battery-80"),
+ pango.Icon("mdi-battery-90"),
+ pango.Icon("mdi-battery")}
+ batteryChargingIcons := [11]*pango.Node{pango.Icon("mdi-battery-charging-outline"),
+ pango.Icon("mdi-battery-charging-10"),
+ pango.Icon("mdi-battery-charging-20"),
+ pango.Icon("mdi-battery-charging-30"),
+ pango.Icon("mdi-battery-charging-40"),
+ pango.Icon("mdi-battery-charging-50"),
+ pango.Icon("mdi-battery-charging-60"),
+ pango.Icon("mdi-battery-charging-70"),
+ pango.Icon("mdi-battery-charging-80"),
+ pango.Icon("mdi-battery-charging-90"),
+ pango.Icon("mdi-battery-charging-100")}
+ barista.Add(battery.All().Output(func(b battery.Info) bar.Output {
+ switch b.Status {
+ case battery.Disconnected, battery.Unknown:
+ return nil
+ default:
+ var icons [11]*pango.Node
+ var colorScheme string
+ if b.Status == battery.Charging {
+ icons = batteryChargingIcons
+ colorScheme = "good"
+ } else {
+ icons = batteryIcons
+ if b.RemainingPct() <= 10 {
+ colorScheme = "bad"
+ } else if b.RemainingPct() <= 20 {
+ colorScheme = "degraded"
+ } else {
+ colorScheme = "good"
+ }
+ }
+ icon := icons[b.RemainingPct()/10]
+ return outputs.Pango(icon, pango.Textf(" %d%%", b.RemainingPct())).Color(colors.Scheme(colorScheme))
+ }
+ }))
+
+ // Display brightness
+ brightnessHighIcon := pango.Icon("mdi-lightbulb-on")
+ brightnessMidIcon := pango.Icon("mdi-lightbulb-on-outline")
+ brightnessLowIcon := pango.Icon("mdi-lightbulb-outline")
+ ReadBrightness := func(name string) (int, error) {
+ valueStr, err := os.ReadFile("/sys/class/backlight/intel_backlight/" + name)
+ if err != nil {
+ return 0, err
+ }
+ return strconv.Atoi(string(valueStr[:len(valueStr)-1]))
+ }
+ brightnessMax, _ := ReadBrightness("max_brightness") // always non-zero, unless there's an error
+ barista.Add(funcs.Every(time.Second, func(s bar.Sink) {
+ brightness, err := ReadBrightness("brightness")
+ if !s.Error(err) {
+ value := (brightness * 100) / brightnessMax
+ var icon *pango.Node
+ if value <= 30 {
+ icon = brightnessLowIcon
+ } else if value < 70 {
+ icon = brightnessMidIcon
+ } else {
+ icon = brightnessHighIcon
+ }
+ s.Output(outputs.Pango(icon, pango.Textf(" %d%%", value)))
+ }
+ }))
+
+ // Display output volume
+ volumeOffIcon := pango.Icon("mdi-volume-variant-off")
+ volumeLowIcon := pango.Icon("mdi-volume-low")
+ volumeMidIcon := pango.Icon("mdi-volume-medium")
+ volumeHighIcon := pango.Icon("mdi-volume-high")
+ barista.Add(volume.New(pulseaudio.DefaultSink()).Output(func(v volume.Volume) bar.Output {
+ volume := v.Pct()
+ var icon *pango.Node
+ if volume == 0 || v.Mute {
+ icon = volumeOffIcon
+ } else if volume <= 30 {
+ icon = volumeLowIcon
+ } else if volume <= 70 {
+ icon = volumeMidIcon
+ } else {
+ icon = volumeHighIcon
+ }
+ return outputs.Pango(icon, pango.Textf(" %d%%", volume))
+ }))
+
+ // Display microphone volume
+ microphoneOffIcon := pango.Icon("mdi-microphone-off")
+ microphoneIcon := pango.Icon("mdi-microphone")
+ barista.Add(volume.New(pulseaudio.DefaultSource()).Output(func(v volume.Volume) bar.Output {
+ volume := v.Pct() // the value returned by pulseaudio may be weird
+ var icon *pango.Node
+ if volume == 0 || v.Mute {
+ icon = microphoneOffIcon
+ } else {
+ icon = microphoneIcon
+ }
+ return outputs.Pango(icon, pango.Textf(" %d%%", volume))
+ }))
+
+ barista.Add(clock.Local().OutputFormat("2006-01-02 15:04:05"))
+
+ panic(barista.Run())
+}
diff --git a/modules/home-manager/personal/gui/x/i3/default.nix b/modules/home-manager/personal/gui/x/i3/default.nix
new file mode 100644
index 0000000..beae770
--- /dev/null
+++ b/modules/home-manager/personal/gui/x/i3/default.nix
@@ -0,0 +1,56 @@
+{ config, lib, pkgs, ... }@extraArgs:
+
+let cfg = config.personal.x.i3;
+in {
+ imports = [ ./bar ./keybindings.nix ./startup.nix ];
+
+ options.personal.x.i3 = {
+ enable = lib.mkEnableOption "i3" // {
+ default =
+ extraArgs.osConfig.services.xserver.windowManager.i3.enable or false;
+ };
+ };
+
+ config = lib.mkIf cfg.enable {
+ xsession.windowManager.i3 = {
+ enable = cfg.enable;
+ package = lib.mkDefault pkgs.i3-gaps;
+
+ config = {
+ assigns = lib.optionalAttrs (config.personal.profiles.multimedia
+ && (extraArgs.osConfig.programs.steam.enable or true)) {
+ "8: multimedia" = [
+ { class = "^Steam$"; }
+ { class = "Netflix"; }
+ { class = "MUBI"; }
+ { class = "Deezer"; }
+ ];
+ } // lib.optionalAttrs config.personal.profiles.social {
+ "9: social" = [
+ { class = "^Mail$"; }
+ { class = "^thunderbird$"; }
+ { class = "^Signal$"; }
+ ];
+ } // {
+ "10: passwords" = [{
+ # matches <some db>.kbdx [Locked] - KeePassXC
+ title = ".*\\.kbdx \\[Locked\\] - KeePassXC$";
+ }];
+ };
+
+ workspaceAutoBackAndForth = lib.mkDefault true;
+
+ window = {
+ titlebar = lib.mkDefault false;
+ border = lib.mkDefault 0;
+ };
+ floating.titlebar = lib.mkDefault false;
+ gaps = {
+ inner = lib.mkDefault 15;
+ outer = lib.mkDefault 5;
+ };
+ };
+ };
+ programs.rofi.enable = lib.mkDefault true;
+ };
+}
diff --git a/modules/home-manager/personal/gui/x/i3/keybindings.nix b/modules/home-manager/personal/gui/x/i3/keybindings.nix
new file mode 100644
index 0000000..3781867
--- /dev/null
+++ b/modules/home-manager/personal/gui/x/i3/keybindings.nix
@@ -0,0 +1,47 @@
+{ config, lib, pkgs, ... }:
+
+let
+ brightnessctl = "${pkgs.brightnessctl}/bin/brightnessctl";
+ brightnessctlKbd = "${brightnessctl} --device dell:kbd_backlight";
+ volumectl = "${pkgs.pulseaudio}/bin/pactl";
+ screenshot = "${pkgs.shutter}/bin/shutter";
+
+ modifier = "Mod4";
+in {
+ xsession.windowManager.i3.config = {
+ inherit modifier;
+
+ keybindings = lib.mkOptionDefault {
+ # launching apps
+ "${modifier}+Control+Return" = ''exec "$EDITOR"'';
+ "${modifier}+Shift+Return" = ''exec "$BROWSER"'';
+ "${modifier}+d" = lib.mkIf config.programs.rofi.enable
+ ''exec "rofi -modi drun,filebrowser,run,window -show drun"'';
+
+ # exiting
+ "${modifier}+Shift+e" = "exec i3-msg exit";
+ "${modifier}+l" =
+ "exec ${config.personal.home.lockscreen}/bin/lockscreen.sh";
+
+ # media keys
+ "XF86MonBrightnessUp" = "exec ${brightnessctl} set 5%+";
+ "XF86MonBrightnessDown" = "exec ${brightnessctl} set 5%-";
+ "XF86AudioRaiseVolume" =
+ "exec ${volumectl} set-sink-volume @DEFAULT_SINK@ +5%";
+ "XF86AudioLowerVolume" =
+ "exec ${volumectl} set-sink-volume @DEFAULT_SINK@ -5%";
+ "XF86AudioMute" = "exec ${volumectl} set-sink-mute @DEFAULT_SINK@ toggle";
+ "Shift+XF86AudioRaiseVolume" =
+ "exec ${volumectl} set-source-volume @DEFAULT_SOURCE@ +5%";
+ "Shift+XF86AudioLowerVolume" =
+ "exec ${volumectl} set-source-volume @DEFAULT_SOURCE@ -5%";
+ "XF86AudioMicMute" =
+ "exec ${volumectl} set-source-mute @DEFAULT_SOURCE@ toggle";
+ "XF86KbdBrightnessUp" = ''
+ exec ${brightnessctlKbd} set \
+ $(( $(${brightnessctlKbd} max) - $(${brightnessctlKbd} get) ))
+ '';
+ "Print" = "exec ${screenshot}";
+ };
+ };
+}
diff --git a/modules/home-manager/personal/gui/x/i3/startup.nix b/modules/home-manager/personal/gui/x/i3/startup.nix
new file mode 100644
index 0000000..9baf388
--- /dev/null
+++ b/modules/home-manager/personal/gui/x/i3/startup.nix
@@ -0,0 +1,25 @@
+{ config, lib, pkgs, ... }:
+
+{
+ xsession.windowManager.i3.config.startup = let
+ autostart = { command, always ? false, notification ? false }: {
+ inherit command always notification;
+ };
+ autostartIf = cond: args: lib.optional cond (autostart args);
+ in [
+ (autostart { command = "rfkill block bluetooth"; })
+ (autostart { command = "keepassxc"; })
+ ]
+ ++ autostartIf config.programs.thunderbird.enable { command = "thunderbird"; }
+ ++ autostartIf config.personal.profiles.social { command = "signal-desktop"; }
+ # ++ autostartIf config.services.redshift.enable {
+ # command = "systemctl --user start redshift";
+ # }
+ ++ autostartIf (config.personal.home.wallpaper != null) {
+ command = "${pkgs.feh}/bin/feh --bg-scale ${config.personal.home.wallpaper}";
+ }
+ # ++ autostartIf config.services.xidlehook.enable {
+ # command = "systemctl --user start xidlehook.service";
+ # }
+ ;
+}
diff --git a/modules/home-manager/personal/gui/x/idlehook.nix b/modules/home-manager/personal/gui/x/idlehook.nix
new file mode 100644
index 0000000..129a9f8
--- /dev/null
+++ b/modules/home-manager/personal/gui/x/idlehook.nix
@@ -0,0 +1,22 @@
+{ config, lib, pkgs, ... }:
+
+let
+ brightnessctl = "${pkgs.brightnessctl}/bin/brightnessctl";
+in {
+ config.services.xidlehook = {
+ enable = lib.mkDefault config.personal.x.enable;
+ not-when-fullscreen = lib.mkDefault true;
+ not-when-audio = lib.mkDefault true;
+ timers = [
+ {
+ delay = 120;
+ command = "${brightnessctl} set 10%-";
+ canceller = "${brightnessctl} set +10%";
+ }
+ {
+ delay = 180;
+ command = config.personal.home.lockscreen;
+ }
+ ];
+ };
+}
diff --git a/modules/home-manager/personal/profiles.nix b/modules/home-manager/personal/profiles.nix
new file mode 100644
index 0000000..25722f5
--- /dev/null
+++ b/modules/home-manager/personal/profiles.nix
@@ -0,0 +1,157 @@
+{ config, lib, pkgs, ... }:
+
+let
+ cfg = config.personal.profiles;
+ mkEnableProfileOption = name: lib.mkEnableOption "${name} profile";
+in {
+ options.personal.profiles = {
+ dev = mkEnableProfileOption "development";
+ social = mkEnableProfileOption "social";
+ syncing = mkEnableProfileOption "syncing";
+ multimedia = mkEnableProfileOption "video";
+ };
+
+ config = lib.mkMerge [
+ (lib.mkIf cfg.dev {
+ home.packages = with pkgs; [ gnupg python3 ];
+ programs = {
+ alacritty.enable = lib.mkDefault config.personal.gui.enable;
+ direnv.enable = lib.mkDefault true;
+ emacs.enable = lib.mkDefault true;
+ git.enable = lib.mkDefault true;
+ };
+
+ home.shellAliases = {
+ mkenv = ''
+ cp ~/.config/venv-manager/shell-template.nix ./shell.nix ;
+ echo "use_nix" >> .envrc ;
+ direnv allow ;
+ $EDITOR shell.nix ;
+ '';
+ };
+
+ services.gpg-agent = {
+ enable = true;
+ enableSshSupport = true;
+ };
+
+ home.file = {
+ ".config/latexmkrc".text =
+ builtins.readFile config.personal.home.dotfiles.latexmkrc;
+ ".config/venv-manager/config/default.nix".source =
+ lib.mkDefault config.personal.home.dotfiles.venv-manager;
+ };
+ })
+
+ (lib.mkIf cfg.multimedia {
+ home.packages = with pkgs; [ pavucontrol transmission-gtk vlc ];
+ personal = {
+ gui.enable = lib.mkForce true;
+ firefox.webapps = [
+ {
+ name = "Netflix";
+ genericName = "Streaming service";
+ icon = "${pkgs.personal.netflixIcon}";
+ comment = "Unlimited movies, TV shows, and more.";
+ url = "https://www.netflix.com/fr-en/login";
+ categories = [ "AudioVideo" "Video" "Player" ];
+ }
+ {
+ name = "MUBI";
+ genericName = "Streaming service";
+ icon = "${pkgs.personal.mubiIcon}";
+ comment = "Watch hand-picked cinema.";
+ url = "https://mubi.com";
+ categories = [ "AudioVideo" "Video" "Player" ];
+ }
+ {
+ name = "Deezer";
+ genericName = "Streaming service";
+ icon = "${pkgs.personal.deezerIcon}";
+ comment = "Listen to music online";
+ url = "https://deezer.com/login";
+ categories = [ "AudioVideo" "Audio" "Player" "Music" ];
+ }
+ ];
+ };
+ })
+
+ (lib.mkIf cfg.social {
+ home.packages = with pkgs;
+ lib.optionals config.personal.gui.enable [ signal-desktop ];
+ programs.thunderbird.enable = lib.mkDefault config.personal.gui.enable;
+ accounts.email.accounts = let
+ gpg = {
+ key = "DFC1660846EEA97C059F18534EF515441E635D36";
+ signByDefault = true;
+ };
+ thunderbirdSettings = id: {
+ "mail.identity.id_${id}.fcc_folder_picker_mode" = 0;
+ };
+ in {
+ personal = {
+ inherit gpg;
+ address = "quentin@aristote.fr";
+ userName = "quentin@aristote.fr";
+ realName = "Quentin Aristote";
+ folders = {
+ drafts = "Inbox/Brouillons";
+ inbox = "Inbox";
+ sent = "Inbox/Envoyés";
+ trash = "Inbox/Corbeille";
+ };
+ imap = {
+ host = "ssl0.ovh.net";
+ port = 993;
+ };
+ smtp = {
+ host = "ssl0.ovh.net";
+ port = 465;
+ };
+ thunderbird = {
+ enable = true;
+ profiles = [ "all" "personal" ];
+ settings = thunderbirdSettings;
+ };
+ };
+ work = {
+ inherit gpg;
+ address = "quentin.aristote@ens.fr";
+ userName = "qaristote";
+ realName = "Quentin Aristote";
+ aliases = [
+ "quentin.aristote@ens.psl.eu"
+ "qaristote@clipper.ens.fr"
+ "qaristote@clipper.ens.psl.eu"
+ ];
+ folders = {
+ drafts = "Drafts";
+ inbox = "Inbox";
+ sent = "Sent";
+ trash = "Trash";
+ };
+ imap = {
+ host = "clipper.ens.fr";
+ port = 993;
+ };
+ smtp = {
+ host = "clipper.ens.fr";
+ port = 465;
+ };
+ thunderbird = {
+ enable = true;
+ profiles = [ "all" "work" ];
+ settings = thunderbirdSettings;
+ };
+ };
+ };
+ })
+
+ (lib.mkIf cfg.syncing {
+ services = {
+ kdeconnect.enable = lib.mkDefault true;
+ syncthing.enable = lib.mkDefault true;
+ };
+ })
+ ];
+}
diff --git a/modules/home-manager/personal/programs/alacritty.nix b/modules/home-manager/personal/programs/alacritty.nix
new file mode 100644
index 0000000..afecfc9
--- /dev/null
+++ b/modules/home-manager/personal/programs/alacritty.nix
@@ -0,0 +1,21 @@
+{ config, lib, ... }:
+
+{
+ programs.alacritty.settings = {
+ window = {
+ padding = {
+ x = 10;
+ y = 10;
+ };
+ dimensions = {
+ lines = 75;
+ columns = 100;
+ };
+ };
+
+ font = { size = 8.0; };
+ };
+
+ xsession.windowManager.i3.config.terminal = lib.mkIf config.programs.alacritty.enable "alacritty";
+}
+
diff --git a/modules/home-manager/personal/programs/default.nix b/modules/home-manager/personal/programs/default.nix
new file mode 100644
index 0000000..8b3ba16
--- /dev/null
+++ b/modules/home-manager/personal/programs/default.nix
@@ -0,0 +1,13 @@
+{ ... }:
+
+{
+ imports = [
+ ./alacritty.nix
+ ./direnv.nix
+ ./emacs.nix
+ ./firefox
+ ./git.nix
+ ./rofi.nix
+ ./thunderbird.nix
+ ];
+}
diff --git a/modules/home-manager/personal/programs/direnv.nix b/modules/home-manager/personal/programs/direnv.nix
new file mode 100644
index 0000000..7d87dc2
--- /dev/null
+++ b/modules/home-manager/personal/programs/direnv.nix
@@ -0,0 +1,31 @@
+{ config, lib, pkgs, ... }:
+
+let cfg = config.programs.direnv;
+in {
+ programs.direnv.nix-direnv.enable = true;
+
+ systemd.user = lib.mkIf cfg.enable
+ (pkgs.personal.lib.homeManager.serviceWithTimer "direnv-clean-update" {
+ Unit = {
+ Description =
+ "Remove old virtual environments and update the current ones";
+ After = [ "network-online.target" ];
+ };
+ Service = {
+ Type = "oneshot";
+ ExecSearchPath =
+ "${pkgs.coreutils}/bin:${pkgs.findutils}/bin:${pkgs.direnv}/bin:/bin/sh";
+ WorkingDirectory = "${config.home.homeDirectory}";
+ ExecStart = ''
+ find -type d -name .direnv \
+ -execdir /bin/sh -c "rm -f .direnv/{nix,flake}-profile*" \; \
+ -execdir direnv exec . true \;
+ '';
+ };
+ Timer = {
+ Persistent = true;
+ OnCalendar = "daily";
+ };
+ Install = { WantedBy = [ "default.target " ]; };
+ });
+}
diff --git a/modules/home-manager/personal/programs/emacs.nix b/modules/home-manager/personal/programs/emacs.nix
new file mode 100644
index 0000000..2189541
--- /dev/null
+++ b/modules/home-manager/personal/programs/emacs.nix
@@ -0,0 +1,59 @@
+{ config, lib, pkgs, ... }:
+
+let
+ cfg = config.programs.emacs;
+ spacemacs-update-script = pkgs.callPackage ({ emacs, git }:
+ pkgs.writeShellApplication {
+ name = "spacemacs-update";
+
+ runtimeInputs = [ emacs git ];
+
+ text = ''
+ git checkout develop
+ git pull
+ git checkout local
+ git merge develop
+ emacs --fg-daemon=update-daemon \
+ --eval '(progn
+ (configuration-layer/update-packages "no-confirmation")
+ (spacemacs/kill-emacs))'
+ '';
+ }) { emacs = cfg.package; };
+in {
+ config = lib.mkIf cfg.enable {
+ services.emacs = {
+ enable = lib.mkDefault true;
+ client.enable = lib.mkDefault true;
+ startWithUserSession = lib.mkDefault true;
+ };
+ home.sessionVariables.EDITOR = "emacsclient --create-frame";
+
+ # add some packages necessary in spacemacs
+ programs.emacs.extraPackages =
+ lib.mkDefault (ep: with ep; [ emacsql-sqlite emacsql-sqlite3 ]);
+ home.packages = with pkgs; [ gnutar source-code-pro ];
+
+ # spacemacs dotfile
+ home.file.".spacemacs.d/init.el".source =
+ lib.mkDefault config.personal.home.dotfiles.spacemacs;
+
+ # service to update spacemacs
+ systemd.user =
+ (pkgs.personal.lib.homeManager.serviceWithTimer "spacemacs-update" {
+ Unit = {
+ Description = "Update Spacemacs by pulling the develop branch";
+ After = [ "network-online.target" "emacs.service" ];
+ };
+ Service = {
+ Type = "oneshot";
+ WorkingDirectory = "${config.home.homeDirectory}/.emacs.d/";
+ ExecStart = "${spacemacs-update-script}";
+ };
+ Timer = {
+ Persistent = true;
+ OnCalendar = "daily";
+ };
+ Install = { WantedBy = [ "default.target" ]; };
+ });
+ };
+}
diff --git a/modules/home-manager/personal/programs/firefox/default.nix b/modules/home-manager/personal/programs/firefox/default.nix
new file mode 100644
index 0000000..1e97c40
--- /dev/null
+++ b/modules/home-manager/personal/programs/firefox/default.nix
@@ -0,0 +1,139 @@
+{ config, lib, pkgs, ... }:
+
+with lib;
+let
+ cfg = config.personal.firefox;
+ userjs = pkgs.callPackage ./userjs.nix {
+ inherit (pkgs.personal) arkenfoxUserJS;
+ inherit (pkgs.lib.personal) toUserJS;
+ };
+ engines = import ./engines.nix;
+ userchrome-treestyletabs = ''
+ /* Hide main tabs toolbar */
+ #TabsToolbar {
+ visibility: collapse;
+ }
+ /* Sidebar min and max width removal */
+ #sidebar {
+ max-width: none !important;
+ min-width: 0px !important;
+ }
+ /* Hide sidebar header, when using Tree Style Tab. */
+ #sidebar-box[sidebarcommand="treestyletab_piro_sakura_ne_jp-sidebar-action"] #sidebar-header {
+ visibility: collapse;
+ }
+ '';
+ extensions = with pkgs.personal; [
+ canvasblocker
+ clearurls
+ darkreader
+ neat-url
+ redirector
+ smart-referer
+ temporary-containers
+ tree-style-tab
+ ublock-origin
+ unpaywall
+ url-in-title
+ ];
+ webappsWithIds = (builtins.foldl' ({ counter, value }:
+ { name, ... }@next: {
+ counter = counter + 1;
+ value = value ++ [
+ (next // {
+ id = counter;
+ profileName = lib.toLower name;
+ })
+ ];
+ }) {
+ counter = 0;
+ value = [ ];
+ } cfg.webapps).value;
+in {
+ options.personal.firefox = {
+ webapps = lib.mkOption {
+ type = with lib.types;
+ listOf (submodule {
+ options = let mkTypedOption = type: lib.mkOption { inherit type; };
+ in {
+ name = mkTypedOption str;
+ genericName = mkTypedOption str // { default = ""; };
+ url = mkTypedOption str;
+ comment = mkTypedOption str // { default = ""; };
+ extraUserJS = mkTypedOption lines // { default = ""; };
+ categories = mkTypedOption (listOf str) // { default = [ ]; };
+ icon = mkTypedOption path;
+ };
+ });
+ default = [ ];
+ };
+ };
+
+ config = lib.mkMerge [
+ {
+ programs.firefox.profiles = builtins.foldl' (prev:
+ { name, id, profileName, extraUserJS, ... }:
+ prev // {
+ "${profileName}" = {
+ inherit extensions;
+ id = id + 2;
+ extraConfig = userjs.streaming + extraUserJS;
+ };
+ }) {
+ default = {
+ inherit extensions;
+ id = 0; # isDefault = true
+
+ extraConfig = userjs.default;
+ userChrome = userchrome-treestyletabs;
+ search = {
+ force = lib.mkDefault true;
+ engines = {
+ inherit (engines) Searx;
+ "Bing".metaData.hidden = true;
+ "Google".metaData.hidden = true;
+ "Amazon.fr".metaData.hidden = true;
+ };
+ default = "Searx";
+ order = [ "Searx" "Wikipedia" ];
+ };
+ };
+
+ videoconferencing = {
+ inherit extensions;
+ id = 1;
+
+ extraConfig = userjs.videoconferencing;
+ userChrome = userchrome-treestyletabs;
+ };
+ } webappsWithIds;
+ }
+
+ (lib.mkIf config.programs.firefox.enable {
+ xdg.desktopEntries = let
+ firefoxProfilesDir = "${config.home.homeDirectory}/.mozilla/firefox";
+ firefoxInProfile = profile:
+ ''
+ ${config.programs.firefox.package}/bin/firefox --profile "${firefoxProfilesDir}/${profile}"'';
+ in builtins.foldl' (prev:
+ { name, profileName, url, genericName, icon, comment, categories, ... }:
+ prev // {
+ "${profileName}" = {
+ inherit name genericName icon comment categories;
+ exec = "${firefoxInProfile profileName} ${url}";
+ };
+ }) {
+ videoconferences = {
+ name = "Video Conferences";
+ genericName = "Video conference";
+ comment = "Use video conferencing software in a browser.";
+ exec = "${firefoxInProfile "videoconferencing"}";
+ categories = [ "Network" "VideoConference" ];
+ };
+ } webappsWithIds;
+
+ home.shellAliases.fftmp = "firefox --profile $(mktemp -d)";
+ home.sessionVariables.BROWSER = "firefox";
+ })
+ ];
+}
diff --git a/modules/home-manager/personal/programs/firefox/engines.nix b/modules/home-manager/personal/programs/firefox/engines.nix
new file mode 100644
index 0000000..7ea2830
--- /dev/null
+++ b/modules/home-manager/personal/programs/firefox/engines.nix
@@ -0,0 +1,8 @@
+{
+ Searx = {
+ urls = [{ template = "https://searx.aristote.fr/search?q={searchTerms}"; }];
+ iconUpdateURL =
+ "https://searx.aristote.fr/static/themes/oscar/img/favicon.png";
+ updateInterval = 24 * 60 * 60 * 1000; # every day
+ };
+}
diff --git a/modules/home-manager/personal/programs/firefox/userjs.nix b/modules/home-manager/personal/programs/firefox/userjs.nix
new file mode 100644
index 0000000..ee105b3
--- /dev/null
+++ b/modules/home-manager/personal/programs/firefox/userjs.nix
@@ -0,0 +1,66 @@
+{ arkenfoxUserJS, toUserJS }:
+
+rec {
+ arkenfox = builtins.readFile "${arkenfoxUserJS}";
+ default = arkenfox + toUserJS {
+ "keyword.enabled" = true; # 0801
+ "signon.rememberSignons" = false; # 0901
+ "security.nocertdb" = true; # 1222
+ "media.peerconnection.enabled" = false; # 2001
+ "media.peerconnection.ice.no_host" = true; # 2004
+ "dom.allow_cut_copy" = true; # 2404
+ "dom.battery.enabled" = false; # 2502
+ "permissions.default.xr" = 2; # 2521
+ "privacy.clearOnShutdown.siteSettings" = true; # 2811
+
+ # Personal
+ ## Warnings
+ "browser.tabs.warnOnClose" = false;
+ "browser.tabs.warnOnCloseOtherTabs" = false;
+ ## Updates
+ "app.update.auto" = false;
+ "browser.search.update" = false;
+ ## Appearance
+ "toolkit.legacyUserProfileCustomizations.stylesheets" = true;
+ ## Content behavior
+ "clipboard.autocopy" = false;
+ ## UX behavior
+ "browser.quitShortcut.disabled" = true;
+ "browser.tabs.closeWindowWithLastTab" = false;
+ ## UX features
+ "extensions.pocket.enabled" = false;
+ "identity.fxaccounts.enabled" = false;
+ };
+
+ streaming = default + toUserJS {
+ # Widevine (DRMs)
+ "media.gmp-widevinecdm.enabled" = true;
+ "media.eme.enabled" = true;
+ # Cache
+ "browser.cache.disk.enable" = true;
+ "browser.cache.offline.storage" = true;
+ # Privacy
+ "privacy.clearOnShutdown.cache" = false;
+ "privacy.clearOnShutdown.cookies" = false;
+ "privacy.clearOnShutdown.siteSettings" = false;
+ "privacy.clearOnShutdown.offlineApps" = false;
+ "privacy.resistFingerprinting" = false; # Netflix is whining
+ };
+
+ videoconferencing = default + toUserJS {
+ # IMPORTANT: uncheck "Prevent WebRTC from leaking local IP addresses" in uBlock Origin's settings
+ # NOTE: if using RFP (4501)
+ # some sites, e.g. Zoom, need a canvas site exception [Right Click>View Page Info>Permissions]
+ # Discord video does not work: it thinks you are FF78: use a separate profile or spoof the user agent
+ "media.peerconnection.enabled" = true;
+ "media.peerconnection.ice.no_host" = false; # may or may not be required
+ "webgl.disabled" = false; # required for Zoom
+ "webgl.min_capability_mode" = false;
+ "media.getusermedia.screensharing.enabled" = true; # optional
+ "media.autoplay.blocking_policy" =
+ 0; # optional (otherwise add site exceptions)
+ "javascript.options.wasm" =
+ true; # optional (some platforms may require this)
+ "dom.webaudio.enabled" = true;
+ };
+}
diff --git a/modules/home-manager/personal/programs/git.nix b/modules/home-manager/personal/programs/git.nix
new file mode 100644
index 0000000..5d272dc
--- /dev/null
+++ b/modules/home-manager/personal/programs/git.nix
@@ -0,0 +1,21 @@
+{ lib, pkgs, ... }:
+
+{
+ programs.git = {
+ userName = lib.mkDefault "Quentin Aristote";
+ userEmail = lib.mkDefault "quentin@aristote.fr";
+
+ ignores = builtins.map builtins.readFile
+ (with pkgs.personal; [ emacsGitignore linuxGitignore direnvGitignore ])
+ ++ [
+ # Personal rules
+ ''
+ # Nix
+ shell.nix
+ .nix-gc-roots
+ .tmp
+ result
+ ''
+ ];
+ };
+}
diff --git a/modules/home-manager/personal/programs/rofi.nix b/modules/home-manager/personal/programs/rofi.nix
new file mode 100644
index 0000000..141339c
--- /dev/null
+++ b/modules/home-manager/personal/programs/rofi.nix
@@ -0,0 +1,8 @@
+{ config, lib, ... }:
+
+{
+ programs.rofi = {
+ cycle = lib.mkDefault true;
+ theme = lib.mkDefault config.personal.home.dotfiles.rofi;
+ };
+}
diff --git a/modules/home-manager/personal/programs/thunderbird.nix b/modules/home-manager/personal/programs/thunderbird.nix
new file mode 100644
index 0000000..c3450af
--- /dev/null
+++ b/modules/home-manager/personal/programs/thunderbird.nix
@@ -0,0 +1,35 @@
+{ config, lib, pkgs, ... }:
+
+let
+ configDefault = builtins.readFile "${pkgs.personal.thunderbirdUserJS}"
+ + pkgs.lib.personal.toUserJS {
+ # 0391
+ "mail.bii.alert.show_preview" = false;
+ # 0610
+ "browser.send_pings" = false;
+ # 5004
+ "permissions.memory_only" = false;
+ # 5016
+ "browser.download.folderList" = 1;
+ # 9000
+ "app.update.auto" = false;
+ # 9131
+ "extensions.cardbook.useOnlyEmail" = false;
+ # 9312
+ "calendar.timezone.local" = "Europe/Paris";
+ };
+ profiles = {
+ all = { };
+ personal = { };
+ work = { };
+ };
+in {
+ config = lib.mkMerge [
+ { programs.thunderbird = { inherit profiles; }; }
+ (lib.mkIf config.programs.thunderbird.enable {
+ home.file = lib.concatMapAttrs
+ (name: _: { ".thunderbird/${name}/user.js".text = configDefault; })
+ profiles;
+ })
+ ];
+}