Initial release.
This commit is contained in:
parent
699b3a0760
commit
72bd841f05
8 changed files with 335 additions and 0 deletions
1
.gitignore
vendored
1
.gitignore
vendored
|
@ -1 +1,2 @@
|
||||||
result
|
result
|
||||||
|
*.qcow2
|
55
README.md
Normal file
55
README.md
Normal file
|
@ -0,0 +1,55 @@
|
||||||
|
NixOS-speak
|
||||||
|
===
|
||||||
|
|
||||||
|
## Aims
|
||||||
|
NixOS as of now is [not accessible to blind people](https://github.com/NixOS/nixpkgs/issues/30760), this projects aim is to mend this issue.
|
||||||
|
|
||||||
|
## Getting Started
|
||||||
|
### Getting the installation image
|
||||||
|
As of now an existing installation of Nix is needed (see [Installing a Binary Distribution](https://nixos.org/nix/manual/#ch-installing-binary)).
|
||||||
|
If there are enough people interested I may end up providing pre-built images.
|
||||||
|
|
||||||
|
After installing nix just clone this repo and run
|
||||||
|
```nix
|
||||||
|
nix-build release.nix -A image.<target>
|
||||||
|
```
|
||||||
|
|
||||||
|
The currently available targets are:
|
||||||
|
- minimal
|
||||||
|
- mate
|
||||||
|
|
||||||
|
### Integrate this module into your existing NixOS configuration
|
||||||
|
Installing the speak submodule is as simple as adding:
|
||||||
|
```nix
|
||||||
|
{ config, ... }:
|
||||||
|
|
||||||
|
{
|
||||||
|
imports = [
|
||||||
|
(fetchTarball git.ophanim.de/derped/NixOS-Speak/archive/master.tar.gz)
|
||||||
|
];
|
||||||
|
|
||||||
|
config.speak = {
|
||||||
|
enable = true;
|
||||||
|
config.speakup = {
|
||||||
|
synth = "soft";
|
||||||
|
key_echo = "0";
|
||||||
|
punc_level = "0";
|
||||||
|
reading_punc = "0";
|
||||||
|
soft = {
|
||||||
|
rate = "7";
|
||||||
|
vol = "0";
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
}
|
||||||
|
```
|
||||||
|
to your configuration.
|
||||||
|
|
||||||
|
## Status/Progress
|
||||||
|
Current Feature Progress (more will be added later):
|
||||||
|
- TTY
|
||||||
|
- ✓ espeak
|
||||||
|
- ✓ espeakup
|
||||||
|
- Desktop
|
||||||
|
- ❌ orca
|
||||||
|
- ❌ speechd
|
7
default.nix
Normal file
7
default.nix
Normal file
|
@ -0,0 +1,7 @@
|
||||||
|
{ ... }:
|
||||||
|
|
||||||
|
{
|
||||||
|
imports = [
|
||||||
|
./options/espeak.nix
|
||||||
|
];
|
||||||
|
}
|
17
extra/exampleConfig.nix
Normal file
17
extra/exampleConfig.nix
Normal file
|
@ -0,0 +1,17 @@
|
||||||
|
{ config, ... }:
|
||||||
|
|
||||||
|
{
|
||||||
|
imports = [ ./.. ];
|
||||||
|
config.speak = {
|
||||||
|
enable = true;
|
||||||
|
# runAsRoot = false;
|
||||||
|
config.speakup = {
|
||||||
|
soft = {
|
||||||
|
direct = "1";
|
||||||
|
rate = "7";
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
config.sound.enable = true;
|
||||||
|
}
|
54
extra/mate.nix
Normal file
54
extra/mate.nix
Normal file
|
@ -0,0 +1,54 @@
|
||||||
|
{ config, lib, pkgs, ... }:
|
||||||
|
|
||||||
|
with lib;
|
||||||
|
|
||||||
|
let
|
||||||
|
addToXDGDirs = p: ''
|
||||||
|
if [ -d "${p}/share/gsettings-schemas/${p.name}" ]; then
|
||||||
|
export XDG_DATA_DIRS=$XDG_DATA_DIRS''${XDG_DATA_DIRS:+:}${p}/share/gsettings-schemas/${p.name}
|
||||||
|
fi
|
||||||
|
if [ -d "${p}/lib/girepository-1.0" ]; then
|
||||||
|
export GI_TYPELIB_PATH=$GI_TYPELIB_PATH''${GI_TYPELIB_PATH:+:}${p}/lib/girepository-1.0
|
||||||
|
export LD_LIBRARY_PATH=$LD_LIBRARY_PATH''${LD_LIBRARY_PATH:+:}${p}/lib
|
||||||
|
fi
|
||||||
|
'';
|
||||||
|
in {
|
||||||
|
environment.systemPackages = with pkgs; [
|
||||||
|
orca
|
||||||
|
glib.bin
|
||||||
|
];
|
||||||
|
services.gnome3.at-spi2-core.enable = true;
|
||||||
|
services.xserver = {
|
||||||
|
desktopManager.mate.enable = true;
|
||||||
|
displayManager = {
|
||||||
|
gdm = {
|
||||||
|
enable = true;
|
||||||
|
autoSuspend = false;
|
||||||
|
autoLogin = {
|
||||||
|
enable = true;
|
||||||
|
user = "nixos";
|
||||||
|
};
|
||||||
|
};
|
||||||
|
sessionCommands = ''
|
||||||
|
if test "$XDG_CURRENT_DESKTOP" = "MATE"; then
|
||||||
|
export XDG_MENU_PREFIX=mate-
|
||||||
|
# Let caja find extensions
|
||||||
|
export CAJA_EXTENSION_DIRS=$CAJA_EXTENSION_DIRS''${CAJA_EXTENSION_DIRS:+:}${config.system.path}/lib/caja/extensions-2.0
|
||||||
|
# Let caja extensions find gsettings schemas
|
||||||
|
${concatMapStrings (p: ''
|
||||||
|
if [ -d "${p}/lib/caja/extensions-2.0" ]; then
|
||||||
|
${addToXDGDirs p}
|
||||||
|
fi
|
||||||
|
'') config.environment.systemPackages}
|
||||||
|
# Add mate-control-center paths to some XDG variables because its schemas are needed by mate-settings-daemon, and mate-settings-daemon is a dependency for mate-control-center (that is, they are mutually recursive)
|
||||||
|
${addToXDGDirs pkgs.mate.mate-control-center}
|
||||||
|
# Auto start orca screen-reader
|
||||||
|
GSETTINGS_BACKEND=dconf ${pkgs.glib.bin}/bin/gsettings set org.gnome.desktop.a11y.applications screen-reader-enabled true
|
||||||
|
GSETTINGS_BACKEND=dconf ${pkgs.glib.bin}/bin/gsettings set org.mate.interface accessibility true
|
||||||
|
GSETTINGS_BACKEND=dconf ${pkgs.glib.bin}/bin/gsettings set org.mate.applications-at-visual startup true
|
||||||
|
export GTK_MODULES=gail:atk-bridge
|
||||||
|
fi
|
||||||
|
'';
|
||||||
|
};
|
||||||
|
};
|
||||||
|
}
|
116
options/espeak.nix
Normal file
116
options/espeak.nix
Normal file
|
@ -0,0 +1,116 @@
|
||||||
|
{ config, lib, pkgs, ... }:
|
||||||
|
|
||||||
|
with lib;
|
||||||
|
|
||||||
|
let
|
||||||
|
cfg = config;
|
||||||
|
speak = cfg.speak;
|
||||||
|
in rec {
|
||||||
|
options.speak = {
|
||||||
|
enable = mkOption {
|
||||||
|
type = types.bool;
|
||||||
|
default = false;
|
||||||
|
description = ''
|
||||||
|
Enable NixOS speak module.
|
||||||
|
'';
|
||||||
|
};
|
||||||
|
installPackages = mkOption {
|
||||||
|
type = types.bool;
|
||||||
|
default = true;
|
||||||
|
description = ''
|
||||||
|
Add spech related packages to environment.
|
||||||
|
'';
|
||||||
|
};
|
||||||
|
user = mkOption {
|
||||||
|
type = types.str;
|
||||||
|
default = "root";
|
||||||
|
description = ''
|
||||||
|
User which runs services like espeakup and speech-dispatcher.
|
||||||
|
User needs to be in audio group.
|
||||||
|
'';
|
||||||
|
};
|
||||||
|
config = {
|
||||||
|
speakup = mkOption {
|
||||||
|
type = types.attrs;
|
||||||
|
default = {};
|
||||||
|
example = ''
|
||||||
|
{
|
||||||
|
synth = "soft";
|
||||||
|
punc_level = "0";
|
||||||
|
reading_punc = "0";
|
||||||
|
soft = {
|
||||||
|
rate = "6";
|
||||||
|
};
|
||||||
|
}
|
||||||
|
'';
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
config = mkIf speak.enable rec {
|
||||||
|
boot.kernelModules = [ "speakup_soft" ];
|
||||||
|
nixpkgs.config.packageOverrides = {
|
||||||
|
espeakup = pkgs.callPackage ../pkgs/espeakup.nix {};
|
||||||
|
};
|
||||||
|
|
||||||
|
# needed for orca
|
||||||
|
services.gnome3.at-spi2-core.enable = mkDefault (cfg.services.xserver.enable);
|
||||||
|
|
||||||
|
# allow users in the audio group to use and configure speakup_soft
|
||||||
|
services.udev.extraRules = ''
|
||||||
|
KERNEL=="synth", SUBSYSTEM=="misc", GROUP="audio", MODE="0660"
|
||||||
|
KERNEL=="softsynth", SUBSYSTEM=="misc", GROUP="audio", MODE="0660"
|
||||||
|
KERNEL=="softsynthu", SUBSYSTEM=="misc", GROUP="audio", MODE="0660"
|
||||||
|
'';
|
||||||
|
|
||||||
|
# See https://aur.archlinux.org/cgit/aur.git/tree/espeakup.service?h=espeakup-git
|
||||||
|
systemd.services = {
|
||||||
|
speakup-configure = let
|
||||||
|
# This whole thing still feels a little bit awkward
|
||||||
|
pathList = collect (v: isList v) (mapAttrsRecursive (p: v: p) speak.config.speakup);
|
||||||
|
mkCommand = p: v: "echo ${v} > /sys/accessibility/speakup/${p}";
|
||||||
|
commandList = (map (l: (mkCommand (concatStringsSep "/" l) (attrByPath l "0" speak.config.speakup))) pathList);
|
||||||
|
in {
|
||||||
|
enable = true;
|
||||||
|
description = "configure speakup.";
|
||||||
|
wantedBy = [ "default.target" ];
|
||||||
|
wants = [ "systemd-udev-settle.service" ];
|
||||||
|
after = [ "systemd-udev-settle.service" "sound.target" ];
|
||||||
|
script = (concatStringsSep "\n" commandList);
|
||||||
|
serviceConfig.Type = "oneshot";
|
||||||
|
};
|
||||||
|
espeakup = {
|
||||||
|
enable = (speak.user == "root");
|
||||||
|
description = "Software speech output system wide settings.";
|
||||||
|
wantedBy = [ "default.target" ];
|
||||||
|
wants = [ "systemd-udev-settle.service" ];
|
||||||
|
after = [ "systemd-udev-settle.service" "sound.target" ];
|
||||||
|
|
||||||
|
serviceConfig = {
|
||||||
|
Type = "forking";
|
||||||
|
ExecStart = "${pkgs.espeakup}/bin/espeakup";
|
||||||
|
ExecStop = "${pkgs.utillinux.bin}/bin/kill -HUP $MAINPID";
|
||||||
|
Restart= "always";
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
systemd.user.services.espeakup = {
|
||||||
|
enable = (speak.user != "root");
|
||||||
|
description = "Software speech output system wide settings.";
|
||||||
|
wantedBy = [ "default.target" ];
|
||||||
|
wants = [ "systemd-udev-settle.service" ];
|
||||||
|
after = [ "systemd-udev-settle.service" "sound.target" ];
|
||||||
|
|
||||||
|
serviceConfig = {
|
||||||
|
Type = "forking";
|
||||||
|
ExecStart = "${pkgs.espeakup}/bin/espeakup";
|
||||||
|
ExecStop = "${pkgs.utillinux.bin}/bin/kill -HUP $MAINPID";
|
||||||
|
Restart= "always";
|
||||||
|
};
|
||||||
|
};
|
||||||
|
environment.systemPackages = optionals speak.installPackages (with pkgs; [
|
||||||
|
(lowPrio espeak-classic) espeak-ng
|
||||||
|
espeakup
|
||||||
|
]);
|
||||||
|
};
|
||||||
|
}
|
26
pkgs/espeakup.nix
Normal file
26
pkgs/espeakup.nix
Normal file
|
@ -0,0 +1,26 @@
|
||||||
|
{ stdenv, fetchFromGitHub
|
||||||
|
, espeak-classic }:
|
||||||
|
|
||||||
|
stdenv.mkDerivation rec {
|
||||||
|
name = "espeakup";
|
||||||
|
version = "0.80.${rev}";
|
||||||
|
rev = "e69d61b2d88d8dc679558dea03c48130127102ac";
|
||||||
|
|
||||||
|
buildInputs = [ espeak-classic ];
|
||||||
|
|
||||||
|
src = fetchFromGitHub {
|
||||||
|
owner = "williamh";
|
||||||
|
repo = name;
|
||||||
|
inherit rev;
|
||||||
|
sha256 = "0zs5asvxavbibpi98pnhl9y2yc701nxf7h17xm6a1q3liippvix1";
|
||||||
|
};
|
||||||
|
|
||||||
|
patchPhase = ''
|
||||||
|
substituteInPlace Makefile --replace "/usr/local" $out
|
||||||
|
'';
|
||||||
|
meta = with stdenv.lib; {
|
||||||
|
description = "espeakup is a program which makes it possible for speakup to use the espeak software synthesizer.";
|
||||||
|
homepage = "https://github.com/williamh/espeakup";
|
||||||
|
platforms = platforms.linux;
|
||||||
|
};
|
||||||
|
}
|
59
release.nix
Normal file
59
release.nix
Normal file
|
@ -0,0 +1,59 @@
|
||||||
|
# This file is heavily inspired by <nixpkgs/nixos/release.nix>
|
||||||
|
{ nixpkgs ? <nixpkgs> # builtins.fetchTarball https://github.com/NixOS/nixpkgs-channels/archive/nixos-20.03.tar.gz
|
||||||
|
, targetSystem ? builtins.currentSystem
|
||||||
|
, speak ? ./. #builtins.fetchGit ./.
|
||||||
|
, configuration ? ./extra/exampleConfig.nix #{ imports = [ (speak + builtins.toPath "/options/espeak.nix") ]; config.speak.enable = true; config.sound.enable = true; }
|
||||||
|
}:
|
||||||
|
|
||||||
|
with builtins;
|
||||||
|
with import (nixpkgs + (toPath "/lib"));
|
||||||
|
|
||||||
|
let
|
||||||
|
pkgs = import nixpkgs { system = targetSystem; };
|
||||||
|
tarball = pkgs.releaseTools.sourceTarball {
|
||||||
|
name = "speak-tarball";
|
||||||
|
src = speak;
|
||||||
|
};
|
||||||
|
modulePath = (nixpkgs + (toPath "/nixos/modules"));
|
||||||
|
makeTarget = target:
|
||||||
|
with import nixpkgs { system = targetSystem; };
|
||||||
|
((import (nixpkgs + (toPath "/nixos/lib/eval-config.nix")) {
|
||||||
|
system = targetSystem;
|
||||||
|
modules = target.modules ++ [ configuration ];
|
||||||
|
}).config.system.build);
|
||||||
|
makeSubTargets = target: {
|
||||||
|
isoImage = hydraJob (makeTarget (mergeAttrsConcatenateValues target {
|
||||||
|
modules = [
|
||||||
|
{ isoImage.isoBaseName = "nixos-${target.name}"; }
|
||||||
|
];
|
||||||
|
})).isoImage;
|
||||||
|
tarball = hydraJob (makeTarget (mergeAttrsConcatenateValues target {
|
||||||
|
modules = [ (modulePath + toPath "/installer/cd-dvd/system-tarball.nix") ];
|
||||||
|
})).tarball;
|
||||||
|
vm = (makeTarget (mergeAttrsConcatenateValues target {
|
||||||
|
modules = [ (modulePath + toPath "/virtualisation/qemu-vm.nix") { config.virtualisation.qemu.options = [ "-soundhw hda" ]; } ];
|
||||||
|
})).vm;
|
||||||
|
};
|
||||||
|
targets = rec {
|
||||||
|
minimal = {
|
||||||
|
name = "minimal";
|
||||||
|
modules = [
|
||||||
|
(modulePath + (toPath "/installer/cd-dvd/installation-cd-minimal.nix"))
|
||||||
|
(modulePath + (toPath "/installer/cd-dvd/channel.nix"))
|
||||||
|
];
|
||||||
|
};
|
||||||
|
mate = {
|
||||||
|
name = "mate";
|
||||||
|
modules = [
|
||||||
|
(modulePath + (toPath "/installer/cd-dvd/installation-cd-graphical-base.nix"))
|
||||||
|
./modules/mate.nix
|
||||||
|
(modulePath + (toPath "/installer/cd-dvd/channel.nix"))
|
||||||
|
];
|
||||||
|
};
|
||||||
|
};
|
||||||
|
allTargets = mapAttrs (name: value: (makeSubTargets value)) targets;
|
||||||
|
in {
|
||||||
|
inherit tarball;
|
||||||
|
image = allTargets;
|
||||||
|
pkgs.espeakup = hydraJob (pkgs.callPackage ./pkgs/espeakup.nix {});
|
||||||
|
}
|
Loading…
Reference in a new issue