{ config, lib, pkgs, ... }: with lib; with types; let # Functions for internal use {{{ generateOption = name: value: if isBool value then "OPTIONS=${if value then "" else "!"}${name}" else "OPTIONS=${name}:${toString value}"; generateHilite = field: settings: let createHiliteString = trigger: color: "/${trigger}/${color}"; hilite_strings = mapAttrsToList createHiliteString settings; in "OPTIONS=hilite_status:${field}${concatStrings hilite_strings}"; generateMsgType = action: messages: let createMsgTypeString = message: ''MSGTYPE=${action} "${message}"''; msg_type_strings = map createMsgTypeString messages; in concatStringsSep "\n" msg_type_strings; generateMenuColor = regex: color: ''MENUCOLOR="${regex}"=${color}''; # }}} # Generate base configuration {{{ generateConfig = { nethack_options, hilite_status, msg_types, menu_colors, ... } @ config: let all_configs = (mapAttrsToList generateOption nethack_options) ++ (mapAttrsToList generateHilite hilite_status) ++ (mapAttrsToList generateMsgType msg_types) ++ (mapAttrsToList generateMenuColor menu_colors); in concatStringsSep "\n" all_configs; # }}} # Generate choose options {{{ generateChoose = choose_config: if choose_config == {} then "" else let generateChooseOption = name: config: "[${name}]\n" + generateConfig config; choose_options = mapAttrsToList (n: v: generateChooseOption n v) choose_config; choose_names = concatStringsSep "," (attrNames choose_config); in "CHOOSE=${choose_names}\n${concatStringsSep "\n" choose_options}"; # }}} # Generate whole .nethackrc {{{ generateNethackrc = nethack_config: let base_config = generateConfig nethack_config; choose_config = generateChoose nethack_config.choose_options; in base_config + "\n" + choose_config; # }}} in { # Options definitions {{{ options.programs.nethack = { enable = mkEnableOption "nethack configuration"; package = mkOption { type = types.package; default = pkgs.nethack; description = "Nethack package to install"; }; nethack_options = mkOption { type = attrsOf (oneOf [bool int str]); default = {}; description = "Nethack options"; example = literalExpression '' { boulder = "0"; windowtype = "curses"; statuslines = 3; autopickup = true; } ''; }; hilite_status = mkOption { type = attrsOf (attrsOf str); default = {}; description = "Status hilites options set"; example = literalExpression '' { hitpoints = { "100%" = "grey&normal"; "<100%" = "green&normal"; "<66%" = "yellow&normal"; "<50%" = "orange&normal"; "<33%" = "red&bold"; }; gold.up = "yellow"; gold.down = "brown"; } ''; }; menu_colors = mkOption { type = attrsOf str; default = {}; description = "Set of MENUCOLOR= options"; }; msg_types = mkOption { type = attrsOf (listOf str); default = {}; description = "Set of MSGTYPE= options"; example = literalExpression '' { hide = [ "You swap places with .*" "Your tentacles suck the .*" ]; norep = [ "You see here a.*" ]; } ''; }; # Choose options {{{ choose_options = mkOption { type = attrsOf (submodule { options = { nethack_options = mkOption { type = attrsOf (oneOf [bool int str]); default = {}; description = "Nethack options"; example = literalExpression '' { boulder = "0"; windowtype = "curses"; statuslines = 3; autopickup = true; } ''; }; hilite_status = mkOption { type = attrsOf (attrsOf str); default = {}; description = "Status hilites options set"; example = literalExpression '' { hitpoints = { "100%" = "grey&normal"; "<100%" = "green&normal"; "<66%" = "yellow&normal"; "<50%" = "orange&normal"; "<33%" = "red&bold"; }; gold.up = "yellow"; gold.down = "brown"; } ''; }; menu_colors = mkOption { type = attrsOf str; default = {}; description = "Set of MENUCOLOR= options"; }; msg_types = mkOption { type = attrsOf (listOf str); default = {}; description = "Set of MSGTYPE= options"; example = literalExpression '' { hide = [ "You swap places with .*" "Your tentacles suck the .*" ]; norep = [ "You see here a.*" ]; } ''; }; }; }); default = {}; description = "Set of CHOOSE= configurations"; example = literalExpression '' { elf-wiz = { options = { race = "elf"; role = "wizard"; }; }; tourist.options = { role = "tourist"; gender = "male"; }; } ''; }; # }}} }; # }}} config = let cfg = config.programs.nethack; in { home = { packages = mkIf cfg.enable [ cfg.package ]; file = { ".nethackrc" = { inherit (cfg) enable; text = generateNethackrc cfg; }; }; }; }; } # vim: et ts=2 sw=2