{ config, lib, nixosConfig, pkgs, ... }: let mpv-prescalers = pkgs.fetchFromGitHub { owner = "bjin"; repo = "mpv-prescalers"; rev = "b37d0f12223720f5ce48e149678162ae0a984176"; sha256 = "1mmf5827qsyph0wqkyvi7zfng1cskkapngn5hf9073zc61n4398y"; meta.license = lib.licenses.lgpl3Plus; }; shaders = { fsrcnnx_x2 = pkgs.fetchurl { url = "https://github.com/igv/FSRCNN-TensorFlow/releases/download/1.1/FSRCNNX_x2_8-0-4-1.glsl"; sha256 = "03qv0l3b1bznarlv0jpi4gqg1zg3khsw5cp8pmabg73k0xpcwqix"; meta.license = lib.licenses.mit; }; SSimDownscaler = pkgs.fetchurl { url = "https://gist.github.com/igv/36508af3ffc84410fe39761d6969be10/raw/ac09db2c0664150863e85d5a4f9f0106b6443a12/SSimDownscaler.glsl"; sha256 = "1c3fp6llg0n8zdxadsg6g3kcvhqvikalbc9q61zgwvsx8q3d8rph"; meta.license = lib.licenses.lgpl3Plus; }; KrigBilateral = pkgs.fetchurl { url = "https://gist.github.com/igv/a015fc885d5c22e6891820ad89555637/raw/c471ef6dcbd3c4a977e1c95dc40944ee38fad08a/KrigBilateral.glsl"; sha256 = "11s0h6i0y3h2nrfp6lax6hzwvjbn93akjr6d61jrmz09zdf1iwmc"; meta.license = lib.licenses.lgpl3Plus; }; }; gallery-view = pkgs.fetchFromGitHub { owner = "occivink"; repo = "mpv-gallery-view"; rev = "5139d346de67e8dbee8c8983777026502d6bc627"; sha256 = "1xcl31rpb6kp479kil4srkclw9ly565zavr65ary9s8795ygfcrs"; meta.license = lib.licenses.gpl2; }; cycleShaders = shaders: "cycle-values glsl-shaders ${lib.concatStringsSep " " shaders}"; in { programs.mpv = { enable = nixosConfig.sbruder.gui.enable; config = { # Main application font osd-font = "DINW07-Medium"; # not included in repository (unfree) # Subtitles sub-font = "Gandhi Sans"; # see osd-font sub-bold = true; sub-font-size = 44; sub-use-margins = false; sub-border-size = 2; # Nicer looking vobsub/PGS subtitles sub-gauss = 0.5; sub-gray = true; # Allow higher volumes volume-max = 150; # Downmix to stereo by default audio-channels = "stereo"; # Allow seeking in streamed media force-seekable = true; # Enable hardware decoding when avaliable hwdec = "auto-safe"; # Do not show images only one second image-display-duration = "inf"; # Better quality (but not too high, otherwise too high frame drop) profile = "gpu-hq"; deband = false; dither-depth = "auto"; # Lossless screenshots screenshot-format = "png"; # Use youtube-dl’s format configuration ytdl-format = "ytdl"; }; bindings = { # Audio filter bs2b (for headphones) "b" = "af toggle bs2b"; # Toggle debanding "D" = "cycle deband"; # Variable correction of audio pitch when changing speed "k" = "cycle-values audio-pitch-correction no yes"; # Reverse cycling for audio and video (shift modifier on german keyboard layout) "'" = "cycle audio down"; "-" = "cycle video down"; # Cycle between audio downmixes "c" = "cycle-values audio-channels stereo mono auto"; # Cycle between smart scalers (and /dev/null = disabled) "K" = cycleShaders [ "${mpv-prescalers}/compute/ravu-lite-r4.hook" "${mpv-prescalers}/compute/ravu-lite-r3.hook" "${mpv-prescalers}/compute/ravu-lite-r2.hook" "/dev/null" ]; "Alt+K" = cycleShaders [ "${mpv-prescalers}/compute/ravu-zoom-r4-yuv.hook" "${mpv-prescalers}/compute/ravu-zoom-r3-yuv.hook" "${mpv-prescalers}/compute/ravu-zoom-r2-yuv.hook" "/dev/null" ]; "Alt+k" = cycleShaders [ "${mpv-prescalers}/compute/nnedi3-nns256-win8x4.hook" "${mpv-prescalers}/compute/nnedi3-nns128-win8x4.hook" "/dev/null" ]; # Toggle pitchcontrol "Ctrl+p" = "script-message-to pitchcontrol toggle"; # more granular panning "Alt+left" = "add video-pan-x 0.05"; "Alt+right" = "add video-pan-x -0.05"; "Alt+up" = "add video-pan-y 0.05"; "Alt+down" = "add video-pan-y -0.05"; # sub-delay for fixing 24 empty frames on blu-ray "Alt+z" = "add sub-delay -1"; "Alt+Z" = "add sub-delay +1"; # sponsorblock: set segment boundaries "alt+g" = "script-binding sponsorblock/set_segment"; # Exits with error to not mark the video as watched in ytcc "Shift+q" = "quit-watch-later 1"; }; profiles = let mkVisualiser = width: height: rate: { lavfi-complex = lib.concatStringsSep ";" [ "[aid1]asplit=4[ao][a1][a2][a3]" "[a1]avectorscope=m=lissajous:s=${toString (width / 3)}x${toString (height / 2)}:draw=dot:r=${toString rate}[avectorscope]" "[a2]aresample=44100,showwaves=s=${toString (width / 3 * 2)}x${toString (height / 2)}:mode=p2p:colors=red|lightgreen:r=${toString rate}[showwaves]" "[a3]showcqt=s=${toString width}x${toString (height / 2)}:axis=0:axis_h=0:r=${toString rate}[showcqt]" "[showwaves][avectorscope]hstack=shortest=1[top]" "[top][showcqt]vstack=shortest=1,fps=${toString rate}[vo]" ]; alpha = false; }; in { visualiser = mkVisualiser 1920 1200 30; visualiser-1080 = mkVisualiser 1920 1080 30; visualiser-60 = mkVisualiser 1920 1080 60; visualiser-1080-60 = mkVisualiser 1920 1080 60; hqencode = { ovc = "libx264"; ovcopts-add = "crf=18"; oac = "flac"; audio-format = "s16"; }; lq = { scale = "bicubic_fast"; cscale = "bicubic_fast"; dscale = "bicubic_fast"; }; hq = { scale = "ewa_lanczossharp"; dscale = "mitchell"; linear-downscaling = "no"; # for KrigBilateral cscale = "ewa_lanczos"; glsl-shader = [ "${shaders.SSimDownscaler}" # dscale "${shaders.KrigBilateral}" # cscale "${shaders.fsrcnnx_x2}" # scale ]; }; interpolate = { blend-subtitles = true; video-sync = "display-resample"; interpolation = true; tscale = "box"; tscale-window = "sphinx"; tscale-radius = 1.0; tscale-clamp = 0.0; }; # adapted from https://github.com/mpv-player/mpv/issues/4418#issuecomment-368272929 clear-speed.af-add = "scaletempo=stride=18:overlap=.6:search=10"; }; scripts = with pkgs.mpvScripts; [ pitchcontrol sponsorblock ]; }; # mpv-gallery-view is not compatible with home-manager’s script injection meachanism xdg.configFile."mpv/scripts/gallery-thumbgen-0.lua".source = "${gallery-view}/scripts/gallery-thumbgen.lua"; xdg.configFile."mpv/scripts/gallery-thumbgen-1.lua".source = "${gallery-view}/scripts/gallery-thumbgen.lua"; xdg.configFile."mpv/scripts/gallery-thumbgen-2.lua".source = "${gallery-view}/scripts/gallery-thumbgen.lua"; xdg.configFile."mpv/scripts/gallery-thumbgen-3.lua".source = "${gallery-view}/scripts/gallery-thumbgen.lua"; xdg.configFile."mpv/scripts/lib/gallery.lua".source = "${gallery-view}/scripts/lib/gallery.lua"; xdg.configFile."mpv/scripts/playlist-view.lua".source = "${gallery-view}/scripts/playlist-view.lua"; xdg.configFile."mpv/script-opts/playlist_view.conf".text = '' thumbs_dir=${config.xdg.cacheHome}/thumbnails/mpv ''; home.file."${config.xdg.cacheHome}/thumbnails/mpv/.create".text = ""; xdg.configFile."mpv/script-opts/stats.conf".text = '' font=DINW07-Regular font_mono=DINW07-Regular font_size=10 redraw_delay=0.25 ''; }