Compare commits
No commits in common. "master" and "eww" have entirely different histories.
660 changed files with 4500 additions and 64024 deletions
|
@ -1,19 +0,0 @@
|
|||
name: Discord
|
||||
|
||||
on:
|
||||
- workflow_dispatch
|
||||
- push
|
||||
|
||||
jobs:
|
||||
discord_commits:
|
||||
runs-on: ubuntu-latest
|
||||
name: discord commits
|
||||
if: contains(github.event.head_commit.message, '(servers)')
|
||||
|
||||
steps:
|
||||
- name: Discommit
|
||||
uses: https://github.com/matt1432/discommit@v0.0.2
|
||||
with:
|
||||
discord_webhook: ${{ secrets.DISCORD_WEBHOOK }}
|
||||
api_url: 'https://git.nelim.org/api/v1/repos/$OWNER/$REPO/git/commits/$REF'
|
||||
title: 'New commit containing changes to server configs:'
|
5
.gitattributes
vendored
5
.gitattributes
vendored
|
@ -1,5 +0,0 @@
|
|||
flake.lock -diff
|
||||
flake.nix -diff
|
||||
**/non-declarative-conf -diff
|
||||
**/package-lock.json -diff
|
||||
**/HomeAssistantGenerated -diff
|
22
.gitignore
vendored
22
.gitignore
vendored
|
@ -1,23 +1 @@
|
|||
# Python
|
||||
*.egg-info
|
||||
|
||||
# NPM
|
||||
*node_modules
|
||||
*build/
|
||||
|
||||
# Direnv
|
||||
*.direnv/
|
||||
|
||||
# Generated by nix
|
||||
result*
|
||||
!results/
|
||||
.nixd.json
|
||||
|
||||
## AGS
|
||||
**/vars.ts
|
||||
**/config.js
|
||||
*icons
|
||||
**/types
|
||||
|
||||
# Other
|
||||
*.temp
|
||||
|
|
16
LICENSE.md
16
LICENSE.md
|
@ -1,16 +0,0 @@
|
|||
MIT No Attribution
|
||||
|
||||
Copyright 2024 Mathis H.
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy of this
|
||||
software and associated documentation files (the "Software"), to deal in the Software
|
||||
without restriction, including without limitation the rights to use, copy, modify,
|
||||
merge, publish, distribute, sublicense, and/or sell copies of the Software, and to
|
||||
permit persons to whom the Software is furnished to do so.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
|
||||
INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A
|
||||
PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
|
||||
HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
||||
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
|
||||
SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
107
README.md
107
README.md
|
@ -1,100 +1,13 @@
|
|||
# My NixOS configs
|
||||
what is currently not working:
|
||||
- plymouth theme has no login prompt
|
||||
- sddm theme flashes white
|
||||
- fixme: swaync acts up with eww
|
||||
- autosign in to keyring
|
||||
|
||||
## AGS
|
||||
what i want to do:
|
||||
- learn flakes
|
||||
- add auto-rotate widget in eww control center
|
||||
|
||||
You might find it weird that most of my config is written in TypeScript.
|
||||
That's because all my desktops run
|
||||
[AGS](https://github.com/Aylur/ags)
|
||||
for UI. Click on
|
||||
[this](https://git.nelim.org/matt1432/nixos-configs/src/branch/master/modules/ags)
|
||||
to see my configuration.
|
||||
# Docs
|
||||
|
||||
I'm also a victim of Stockholm syndrome at this point and make my scripts
|
||||
in TypeScript because it's the scripting language I am most comfortable with.
|
||||
|
||||
## About
|
||||
|
||||
### General
|
||||
|
||||
This repo is the complete configuration of machines I own running NixOS or Nix
|
||||
and any other related smaller projects exposed by a Nix Flake.
|
||||
|
||||
Its main directory structure is based on a flake's
|
||||
[outputs](https://wiki.nixos.org/wiki/Flakes#Output_schema).
|
||||
|
||||
I try to follow a few rules to better organise my Nix code:
|
||||
|
||||
- Every main subdirectory only has an optional `default.nix` and subfolders for each
|
||||
of its attributes.
|
||||
- Inside a subdirectory, if there is non nix code, it will be in a `config` folder.
|
||||
- Every module should not do anything if imported. An enable option should be toggled
|
||||
for it to have any effect.
|
||||
- Any nix file that represents a module should be named `default.nix` (a nix file
|
||||
which is imported directly can be called anything else alongside `default.nix`)
|
||||
|
||||
### Flake Location
|
||||
|
||||
This git repo will always be located at `$FLAKE` (`config.environment.variables.FLAKE`)
|
||||
and symlinked to `/etc/nixos` to have everything where NixOS tools
|
||||
expect things to be.
|
||||
|
||||
ie.
|
||||
|
||||
```bash
|
||||
sudo rm -r /etc/nixos
|
||||
|
||||
echo "$FLAKE" # /home/matt/.nix
|
||||
|
||||
sudo ln -sf /home/matt/.nix /etc/nixos
|
||||
```
|
||||
|
||||
### Subdirectories
|
||||
|
||||
| Output / Directory | Description |
|
||||
| -------------------- | ----------- |
|
||||
| `apps` | [Misc scripts ran from the flake](./apps) |
|
||||
| `configurations` | [device, ISO and nix-on-droid configurations](./configurations) |
|
||||
| `devShells` | [Development shells for a bunch of projects and languages](./devShells) |
|
||||
| `homeManagerModules` | [Modules made for home-manager](./homeManagerModules) |
|
||||
| `inputs` | [Pre-evaluated flake inputs](./inputs) |
|
||||
| `lib` | [Custom Nix functions made easily available](./lib) |
|
||||
| `modules` | [Modules made for NixOS systems](./modules) |
|
||||
| `nixFastChecks` | [Attribute set of derivations exposed by this flake](./nixFastChecks) |
|
||||
| `overlays` | [Nixpkgs overlays](./overlays) |
|
||||
| `packages` | [Some custom packages not available in nixpkgs or modified from it](./packages) |
|
||||
| `results` | Directory where I neatly keep my result symlinks from `nixFastChecks` |
|
||||
| `scopedPackages` | [Some custom package scopes not available in nixpkgs or modified from it](./scopedPackages) |
|
||||
|
||||
### Secrets
|
||||
|
||||
All my secrets are in a private git repo that makes use of
|
||||
[sops-nix](https://github.com/Mic92/sops-nix).
|
||||
I generate `.sops.yaml` from `.sops.nix`:
|
||||
|
||||
```nix
|
||||
let
|
||||
wim = "somekey";
|
||||
binto = "somekey2";
|
||||
in {
|
||||
creation_rules = [
|
||||
{
|
||||
path_regex = "secrets/[^/]+\\.(yaml|json|env|ini)$";
|
||||
key_groups = [
|
||||
{
|
||||
age = [wim binto];
|
||||
}
|
||||
];
|
||||
}
|
||||
];
|
||||
}
|
||||
```
|
||||
|
||||
which is then converted to `.sops.yaml` using
|
||||
[remarshal](https://github.com/remarshal-project/remarshal)
|
||||
and this shell command:
|
||||
|
||||
```bash
|
||||
nix eval --json --file ./.sops.nix | remarshal --if json --of yaml > .sops.yaml
|
||||
```
|
||||
|
||||
TLDR: I **[hate](https://ruudvanasseldonk.com/2023/01/11/the-yaml-document-from-hell)** YAML
|
||||
Since I use my laptop with one user, I symlinked the configs to my home directory following the tutorial [here](https://nixos.wiki/wiki/NixOS_configuration_editors)
|
||||
|
|
116
_outputs.nix
116
_outputs.nix
|
@ -1,116 +0,0 @@
|
|||
{
|
||||
inputs = import ./inputs;
|
||||
|
||||
outputs = inputs @ {
|
||||
self,
|
||||
systems,
|
||||
nixpkgs,
|
||||
secrets,
|
||||
...
|
||||
}: let
|
||||
inherit (self.lib) mkVersion mkNixOS mkNixOnDroid mkPkgs;
|
||||
|
||||
perSystem = attrs:
|
||||
nixpkgs.lib.genAttrs (import systems) (system:
|
||||
attrs (mkPkgs {inherit system nixpkgs;}));
|
||||
in {
|
||||
lib = import ./lib {inherit inputs perSystem;};
|
||||
|
||||
nixOnDroidConfigurations.default =
|
||||
mkNixOnDroid [./configurations/android];
|
||||
|
||||
nixosConfigurations = {
|
||||
# Desktops
|
||||
wim = mkNixOS {
|
||||
extraModules = [
|
||||
./configurations/wim
|
||||
secrets.nixosModules.default
|
||||
];
|
||||
};
|
||||
binto = mkNixOS {
|
||||
cudaSupport = true;
|
||||
extraModules = [./configurations/binto];
|
||||
};
|
||||
|
||||
bbsteamie = mkNixOS {
|
||||
mainUser = "mariah";
|
||||
extraModules = [./configurations/bbsteamie];
|
||||
};
|
||||
|
||||
# NAS
|
||||
nos = mkNixOS {
|
||||
cudaSupport = true;
|
||||
extraModules = [
|
||||
./configurations/nos
|
||||
secrets.nixosModules.nos
|
||||
];
|
||||
};
|
||||
|
||||
# Build / test server
|
||||
servivi = mkNixOS {
|
||||
extraModules = [
|
||||
./configurations/servivi
|
||||
secrets.nixosModules.servivi
|
||||
];
|
||||
};
|
||||
|
||||
# Home-assistant
|
||||
homie = mkNixOS {
|
||||
extraModules = [
|
||||
./configurations/homie
|
||||
secrets.nixosModules.homie
|
||||
];
|
||||
};
|
||||
|
||||
# Cluster
|
||||
thingone = mkNixOS {
|
||||
extraModules = [
|
||||
(import ./configurations/cluster "thingone")
|
||||
secrets.nixosModules.thingy
|
||||
];
|
||||
};
|
||||
thingtwo = mkNixOS {
|
||||
extraModules = [
|
||||
(import ./configurations/cluster "thingtwo")
|
||||
secrets.nixosModules.thingy
|
||||
];
|
||||
};
|
||||
|
||||
live-image = mkNixOS {
|
||||
mainUser = "nixos";
|
||||
extraModules = [./configurations/live-image];
|
||||
};
|
||||
};
|
||||
|
||||
# For nix-fast-build. I use a custom output to alleviate eval time of this flake. ie. when doing nix flake show
|
||||
nixFastChecks = import ./nixFastChecks {inherit perSystem self;};
|
||||
|
||||
homeManagerModules = import ./homeManagerModules {inherit self;};
|
||||
|
||||
nixosModules = import ./modules {inherit self;};
|
||||
|
||||
overlays = import ./overlays {inherit self;};
|
||||
|
||||
apps =
|
||||
perSystem (pkgs:
|
||||
import ./apps {inherit pkgs self;});
|
||||
|
||||
appsPackages =
|
||||
perSystem (pkgs:
|
||||
import ./apps/packages.nix {inherit inputs pkgs;});
|
||||
|
||||
devShells =
|
||||
perSystem (pkgs:
|
||||
import ./devShells {inherit pkgs self;});
|
||||
|
||||
packages =
|
||||
perSystem (pkgs:
|
||||
import ./packages {inherit inputs mkVersion pkgs;});
|
||||
|
||||
scopedPackages =
|
||||
perSystem (pkgs:
|
||||
import ./scopedPackages {inherit inputs mkVersion pkgs;});
|
||||
|
||||
formatter = perSystem (pkgs: pkgs.alejandra);
|
||||
};
|
||||
}
|
|
@ -1,12 +0,0 @@
|
|||
# Apps
|
||||
|
||||
This directory contains every derivations for apps exposed by this flake.
|
||||
|
||||
## List of my apps found in `self.apps`
|
||||
|
||||
| Name | Description |
|
||||
| ---- | ----------- |
|
||||
| `extract-subs` | Extract all `srt` subtitle files from a `mkv` video with the appropriate name. |
|
||||
| `gen-docs` | Generates the READMEs in this repository from nix attributes. |
|
||||
| `pin-inputs` | Takes a list of inputs to pin to their current rev in `flake.lock`. |
|
||||
| `update-sources` | Updates all derivation sources in this repository and generates a commit message for the changes made. |
|
|
@ -1,40 +0,0 @@
|
|||
{
|
||||
lib,
|
||||
src,
|
||||
npmDepsHash,
|
||||
runtimeInputs,
|
||||
buildNpmPackage,
|
||||
meta,
|
||||
makeWrapper,
|
||||
nodejs_latest,
|
||||
jq,
|
||||
...
|
||||
}: let
|
||||
inherit (lib) concatMapStringsSep;
|
||||
inherit (builtins) fromJSON readFile;
|
||||
|
||||
packageJSON = fromJSON (readFile "${src}/package.json");
|
||||
pname = packageJSON.name;
|
||||
inherit (packageJSON) version;
|
||||
in
|
||||
buildNpmPackage {
|
||||
inherit pname version src runtimeInputs npmDepsHash;
|
||||
|
||||
prePatch = ''
|
||||
mv ./tsconfig.json ./project.json
|
||||
sed 's/^ *\/\/.*//' ${./config/tsconfig.json} > ./base.json
|
||||
${jq}/bin/jq -sr '.[0] * .[1] | del(.extends)' ./project.json ./base.json > ./tsconfig.json
|
||||
rm base.json project.json
|
||||
'';
|
||||
|
||||
nativeBuildInputs = [makeWrapper];
|
||||
|
||||
postInstall = ''
|
||||
wrapProgram $out/bin/${pname} \
|
||||
--prefix PATH : ${concatMapStringsSep ":" (p: p + "/bin") runtimeInputs}
|
||||
'';
|
||||
|
||||
nodejs = nodejs_latest;
|
||||
|
||||
meta = {mainProgram = pname;} // meta;
|
||||
}
|
|
@ -1,2 +0,0 @@
|
|||
use flake $FLAKE#node
|
||||
npm ci
|
|
@ -1,451 +0,0 @@
|
|||
import eslint from '@eslint/js';
|
||||
import jsdoc from 'eslint-plugin-jsdoc';
|
||||
import stylistic from '@stylistic/eslint-plugin';
|
||||
import tseslint from 'typescript-eslint';
|
||||
|
||||
|
||||
export default tseslint.config({
|
||||
files: ['**/*.js', '**/*.ts'],
|
||||
ignores: ['node_modules/**', 'types/**'],
|
||||
|
||||
extends: [
|
||||
eslint.configs.recommended,
|
||||
jsdoc.configs['flat/recommended-typescript'],
|
||||
stylistic.configs['recommended-flat'],
|
||||
...tseslint.configs.recommended,
|
||||
...tseslint.configs.stylistic,
|
||||
],
|
||||
|
||||
rules: {
|
||||
// JSDoc settings
|
||||
'jsdoc/tag-lines': ['warn', 'any', { startLines: 1 }],
|
||||
'jsdoc/check-line-alignment': ['warn', 'always', {
|
||||
tags: ['param', 'arg', 'argument', 'property', 'prop'],
|
||||
}],
|
||||
'jsdoc/no-types': 'off',
|
||||
|
||||
// Newer settings
|
||||
'@typescript-eslint/no-extraneous-class': ['off'],
|
||||
'@typescript-eslint/no-implied-eval': ['off'],
|
||||
'class-methods-use-this': 'off',
|
||||
'@stylistic/no-multiple-empty-lines': 'off',
|
||||
|
||||
// Pre-flat config
|
||||
'@typescript-eslint/no-unused-vars': [
|
||||
'error',
|
||||
{
|
||||
args: 'all',
|
||||
argsIgnorePattern: '^_',
|
||||
caughtErrors: 'all',
|
||||
caughtErrorsIgnorePattern: '^_',
|
||||
destructuredArrayIgnorePattern: '^_',
|
||||
varsIgnorePattern: '^_',
|
||||
ignoreRestSiblings: true,
|
||||
},
|
||||
],
|
||||
|
||||
'array-callback-return': [
|
||||
'error',
|
||||
{
|
||||
allowImplicit: true,
|
||||
checkForEach: true,
|
||||
},
|
||||
],
|
||||
'no-constructor-return': [
|
||||
'error',
|
||||
],
|
||||
'no-unreachable-loop': [
|
||||
'error',
|
||||
{
|
||||
ignore: [
|
||||
'ForInStatement',
|
||||
'ForOfStatement',
|
||||
],
|
||||
},
|
||||
],
|
||||
'no-use-before-define': [
|
||||
'error',
|
||||
{
|
||||
functions: false,
|
||||
},
|
||||
],
|
||||
'block-scoped-var': [
|
||||
'error',
|
||||
],
|
||||
'curly': [
|
||||
'warn',
|
||||
],
|
||||
'default-case-last': [
|
||||
'warn',
|
||||
],
|
||||
'default-param-last': [
|
||||
'error',
|
||||
],
|
||||
'eqeqeq': [
|
||||
'error',
|
||||
'smart',
|
||||
],
|
||||
'func-names': [
|
||||
'warn',
|
||||
'never',
|
||||
],
|
||||
'func-style': [
|
||||
'warn',
|
||||
'expression',
|
||||
],
|
||||
'logical-assignment-operators': [
|
||||
'warn',
|
||||
'always',
|
||||
],
|
||||
'no-array-constructor': [
|
||||
'error',
|
||||
],
|
||||
'no-empty-function': [
|
||||
'warn',
|
||||
],
|
||||
'no-empty-static-block': [
|
||||
'warn',
|
||||
],
|
||||
'no-extend-native': [
|
||||
'error',
|
||||
],
|
||||
'no-extra-bind': [
|
||||
'warn',
|
||||
],
|
||||
'no-implicit-coercion': [
|
||||
'warn',
|
||||
],
|
||||
'no-iterator': [
|
||||
'error',
|
||||
],
|
||||
'no-labels': [
|
||||
'error',
|
||||
],
|
||||
'no-lone-blocks': [
|
||||
'error',
|
||||
],
|
||||
'no-lonely-if': [
|
||||
'error',
|
||||
],
|
||||
'no-loop-func': [
|
||||
'error',
|
||||
],
|
||||
'no-magic-numbers': [
|
||||
'error',
|
||||
{
|
||||
ignore: [
|
||||
-1,
|
||||
0.1,
|
||||
0,
|
||||
1,
|
||||
2,
|
||||
3,
|
||||
4,
|
||||
5,
|
||||
10,
|
||||
12,
|
||||
33,
|
||||
66,
|
||||
100,
|
||||
255,
|
||||
360,
|
||||
450,
|
||||
500,
|
||||
1000,
|
||||
],
|
||||
ignoreDefaultValues: true,
|
||||
ignoreClassFieldInitialValues: true,
|
||||
},
|
||||
],
|
||||
'no-multi-assign': [
|
||||
'error',
|
||||
],
|
||||
'no-new-wrappers': [
|
||||
'error',
|
||||
],
|
||||
'no-object-constructor': [
|
||||
'error',
|
||||
],
|
||||
'no-proto': [
|
||||
'error',
|
||||
],
|
||||
'no-return-assign': [
|
||||
'error',
|
||||
],
|
||||
'no-sequences': [
|
||||
'error',
|
||||
],
|
||||
'no-shadow': [
|
||||
'error',
|
||||
{
|
||||
builtinGlobals: true,
|
||||
allow: [
|
||||
'Window',
|
||||
],
|
||||
},
|
||||
],
|
||||
'no-undef-init': [
|
||||
'warn',
|
||||
],
|
||||
'no-undefined': [
|
||||
'error',
|
||||
],
|
||||
'no-useless-constructor': [
|
||||
'warn',
|
||||
],
|
||||
'no-useless-escape': [
|
||||
'off',
|
||||
],
|
||||
'no-useless-return': [
|
||||
'error',
|
||||
],
|
||||
'no-var': [
|
||||
'error',
|
||||
],
|
||||
'no-void': [
|
||||
'off',
|
||||
],
|
||||
'no-with': [
|
||||
'error',
|
||||
],
|
||||
'object-shorthand': [
|
||||
'error',
|
||||
'always',
|
||||
],
|
||||
'one-var': [
|
||||
'error',
|
||||
'never',
|
||||
],
|
||||
'operator-assignment': [
|
||||
'warn',
|
||||
'always',
|
||||
],
|
||||
'prefer-arrow-callback': [
|
||||
'error',
|
||||
],
|
||||
'prefer-const': [
|
||||
'error',
|
||||
],
|
||||
'prefer-object-has-own': [
|
||||
'error',
|
||||
],
|
||||
'prefer-regex-literals': [
|
||||
'error',
|
||||
],
|
||||
'prefer-template': [
|
||||
'warn',
|
||||
],
|
||||
'no-prototype-builtins': 'off',
|
||||
'@typescript-eslint/no-var-requires': [
|
||||
'off',
|
||||
],
|
||||
'@stylistic/array-bracket-newline': [
|
||||
'warn',
|
||||
'consistent',
|
||||
],
|
||||
'@stylistic/array-bracket-spacing': [
|
||||
'warn',
|
||||
'never',
|
||||
],
|
||||
'@stylistic/arrow-parens': [
|
||||
'warn',
|
||||
'always',
|
||||
],
|
||||
'@stylistic/brace-style': [
|
||||
'warn',
|
||||
'stroustrup',
|
||||
],
|
||||
'@stylistic/comma-dangle': [
|
||||
'warn',
|
||||
'always-multiline',
|
||||
],
|
||||
'@stylistic/comma-spacing': [
|
||||
'warn',
|
||||
{
|
||||
before: false,
|
||||
after: true,
|
||||
},
|
||||
],
|
||||
'@stylistic/comma-style': [
|
||||
'error',
|
||||
'last',
|
||||
],
|
||||
'@stylistic/dot-location': [
|
||||
'error',
|
||||
'property',
|
||||
],
|
||||
'@stylistic/function-call-argument-newline': [
|
||||
'warn',
|
||||
'consistent',
|
||||
],
|
||||
'@stylistic/function-paren-newline': [
|
||||
'warn',
|
||||
'consistent',
|
||||
],
|
||||
'@stylistic/indent': [
|
||||
'warn',
|
||||
4,
|
||||
{
|
||||
SwitchCase: 1,
|
||||
ignoreComments: true,
|
||||
ignoredNodes: ['TemplateLiteral > *'],
|
||||
},
|
||||
],
|
||||
'@stylistic/key-spacing': [
|
||||
'warn',
|
||||
{
|
||||
beforeColon: false,
|
||||
afterColon: true,
|
||||
},
|
||||
],
|
||||
'@stylistic/keyword-spacing': [
|
||||
'warn',
|
||||
{
|
||||
before: true,
|
||||
},
|
||||
],
|
||||
'@stylistic/linebreak-style': [
|
||||
'error',
|
||||
'unix',
|
||||
],
|
||||
'@stylistic/lines-between-class-members': [
|
||||
'warn',
|
||||
'always',
|
||||
{
|
||||
exceptAfterSingleLine: true,
|
||||
},
|
||||
],
|
||||
'@stylistic/max-len': [
|
||||
'warn',
|
||||
{
|
||||
code: 105,
|
||||
ignoreComments: true,
|
||||
ignoreTrailingComments: true,
|
||||
ignoreUrls: true,
|
||||
},
|
||||
],
|
||||
'@stylistic/multiline-ternary': [
|
||||
'warn',
|
||||
'always-multiline',
|
||||
],
|
||||
'@stylistic/new-parens': [
|
||||
'error',
|
||||
],
|
||||
'@stylistic/no-mixed-operators': [
|
||||
'warn',
|
||||
],
|
||||
'@stylistic/no-mixed-spaces-and-tabs': [
|
||||
'error',
|
||||
],
|
||||
'@stylistic/no-multi-spaces': [
|
||||
'error',
|
||||
],
|
||||
'@stylistic/no-tabs': [
|
||||
'error',
|
||||
],
|
||||
'@stylistic/no-trailing-spaces': [
|
||||
'error',
|
||||
],
|
||||
'@stylistic/no-whitespace-before-property': [
|
||||
'warn',
|
||||
],
|
||||
'@stylistic/nonblock-statement-body-position': [
|
||||
'error',
|
||||
'below',
|
||||
],
|
||||
'@stylistic/object-curly-newline': [
|
||||
'warn',
|
||||
{
|
||||
consistent: true,
|
||||
},
|
||||
],
|
||||
'@stylistic/object-curly-spacing': [
|
||||
'warn',
|
||||
'always',
|
||||
],
|
||||
'@stylistic/operator-linebreak': [
|
||||
'warn',
|
||||
'after',
|
||||
],
|
||||
'@stylistic/padded-blocks': [
|
||||
'error',
|
||||
'never',
|
||||
],
|
||||
'@stylistic/padding-line-between-statements': [
|
||||
'warn',
|
||||
{
|
||||
blankLine: 'always',
|
||||
prev: '*',
|
||||
next: 'return',
|
||||
},
|
||||
{
|
||||
blankLine: 'always',
|
||||
prev: [
|
||||
'const',
|
||||
'let',
|
||||
'var',
|
||||
],
|
||||
next: '*',
|
||||
},
|
||||
{
|
||||
blankLine: 'any',
|
||||
prev: [
|
||||
'const',
|
||||
'let',
|
||||
'var',
|
||||
],
|
||||
next: [
|
||||
'const',
|
||||
'let',
|
||||
'var',
|
||||
],
|
||||
},
|
||||
{
|
||||
blankLine: 'always',
|
||||
prev: [
|
||||
'case',
|
||||
'default',
|
||||
],
|
||||
next: '*',
|
||||
},
|
||||
],
|
||||
'@stylistic/quote-props': [
|
||||
'error',
|
||||
'consistent-as-needed',
|
||||
],
|
||||
'@stylistic/quotes': [
|
||||
'error',
|
||||
'single',
|
||||
{
|
||||
avoidEscape: true,
|
||||
},
|
||||
],
|
||||
'@stylistic/semi': [
|
||||
'error',
|
||||
'always',
|
||||
],
|
||||
'@stylistic/semi-spacing': [
|
||||
'warn',
|
||||
],
|
||||
'@stylistic/space-before-blocks': [
|
||||
'warn',
|
||||
],
|
||||
'@stylistic/space-before-function-paren': [
|
||||
'warn',
|
||||
'never',
|
||||
],
|
||||
'@stylistic/space-infix-ops': [
|
||||
'warn',
|
||||
],
|
||||
'@stylistic/spaced-comment': [
|
||||
'warn',
|
||||
'always',
|
||||
],
|
||||
'@stylistic/switch-colon-spacing': [
|
||||
'warn',
|
||||
],
|
||||
'@stylistic/wrap-regex': [
|
||||
'warn',
|
||||
],
|
||||
},
|
||||
});
|
|
@ -1,3 +0,0 @@
|
|||
import eslintConf from './eslint.config';
|
||||
|
||||
export default eslintConf;
|
1883
apps/config/package-lock.json
generated
1883
apps/config/package-lock.json
generated
File diff suppressed because it is too large
Load diff
|
@ -1,16 +0,0 @@
|
|||
{
|
||||
"name": "eslint-conf",
|
||||
"version": "0.0.0",
|
||||
"type": "module",
|
||||
"exports": "./index.ts",
|
||||
"devDependencies": {
|
||||
"@eslint/js": "9.20.0",
|
||||
"@stylistic/eslint-plugin": "3.1.0",
|
||||
"eslint": "9.20.1",
|
||||
"eslint-plugin-jsdoc": "50.6.3",
|
||||
"jiti": "2.4.2",
|
||||
"pkg-types": "1.3.1",
|
||||
"typescript": "5.7.3",
|
||||
"typescript-eslint": "8.24.1"
|
||||
}
|
||||
}
|
|
@ -1,25 +0,0 @@
|
|||
{
|
||||
"$schema": "https://json.schemastore.org/tsconfig",
|
||||
"compilerOptions": {
|
||||
// Env
|
||||
"target": "ESNext",
|
||||
"lib": [
|
||||
"ESNext"
|
||||
],
|
||||
// Module
|
||||
"module": "nodenext",
|
||||
"moduleResolution": "bundler",
|
||||
"baseUrl": ".",
|
||||
// Emit
|
||||
"noEmit": true,
|
||||
"newLine": "LF",
|
||||
// Interop
|
||||
"esModuleInterop": true,
|
||||
"allowSyntheticDefaultImports": true,
|
||||
"forceConsistentCasingInFileNames": true,
|
||||
"isolatedModules": true,
|
||||
// Type Checking
|
||||
"strict": true,
|
||||
"noImplicitAny": false
|
||||
}
|
||||
}
|
|
@ -1,10 +0,0 @@
|
|||
{
|
||||
"$schema": "https://json.schemastore.org/tsconfig",
|
||||
"extends": "./tsconfig.base.json",
|
||||
"includes": [
|
||||
"*.ts",
|
||||
"**/*.ts",
|
||||
"*.js",
|
||||
"**/*.js"
|
||||
]
|
||||
}
|
|
@ -1,13 +0,0 @@
|
|||
{
|
||||
pkgs,
|
||||
self,
|
||||
...
|
||||
}: let
|
||||
inherit (pkgs.lib) getExe mapAttrs;
|
||||
|
||||
mkApp = pkg: {
|
||||
program = getExe pkg;
|
||||
type = "app";
|
||||
};
|
||||
in
|
||||
mapAttrs (n: v: mkApp v) self.appsPackages.${pkgs.system}
|
|
@ -1,3 +0,0 @@
|
|||
use flake $FLAKE#subtitles-dev
|
||||
(cd ../config; npm ci)
|
||||
npm ci
|
|
@ -1,17 +0,0 @@
|
|||
{
|
||||
buildApp,
|
||||
ffmpeg-full,
|
||||
...
|
||||
}:
|
||||
buildApp {
|
||||
src = ./.;
|
||||
npmDepsHash = "sha256-+NHetW6zNnJ8bubvuttwjnKGbXfwfcB0FIYpVvj7mjE=";
|
||||
|
||||
runtimeInputs = [
|
||||
ffmpeg-full
|
||||
];
|
||||
|
||||
meta.description = ''
|
||||
Extract all `srt` subtitle files from a `mkv` video with the appropriate name.
|
||||
'';
|
||||
}
|
|
@ -1,3 +0,0 @@
|
|||
import eslintConf from 'eslint-conf';
|
||||
|
||||
export default eslintConf;
|
1646
apps/extract-subs/package-lock.json
generated
1646
apps/extract-subs/package-lock.json
generated
File diff suppressed because it is too large
Load diff
|
@ -1,21 +0,0 @@
|
|||
{
|
||||
"name": "extract-subs",
|
||||
"version": "0.0.0",
|
||||
"bin": "out/bin/app.cjs",
|
||||
"type": "module",
|
||||
"scripts": {
|
||||
"build": "node_ver=$(node -v); esbuild src/app.ts --bundle --platform=node --target=\"node${node_ver:1:2}\" --outfile=out/bin/app.cjs"
|
||||
},
|
||||
"dependencies": {
|
||||
"@types/fluent-ffmpeg": "2.1.27",
|
||||
"fluent-ffmpeg": "2.1.3"
|
||||
},
|
||||
"devDependencies": {
|
||||
"eslint-conf": "file:../config",
|
||||
"@types/node": "22.10.10",
|
||||
"esbuild": "0.24.2",
|
||||
"eslint": "9.19.0",
|
||||
"jiti": "2.4.2",
|
||||
"typescript": "5.7.3"
|
||||
}
|
||||
}
|
|
@ -1,157 +0,0 @@
|
|||
import { spawnSync as spawn } from 'child_process';
|
||||
|
||||
import ffprobe from './ffprobe';
|
||||
import { ISO6393To1 } from './lang-codes';
|
||||
|
||||
/* Types */
|
||||
import { FfprobeStream } from 'fluent-ffmpeg';
|
||||
|
||||
|
||||
const SPAWN_OPTS = {
|
||||
stdio: [process.stdin, process.stdout, process.stderr],
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* These are the cli arguments
|
||||
*
|
||||
* @param videoPath the directory in which we want to sync the subtitles
|
||||
* @param languages a comma-separated list of languages (3 letters) to sync the subtitles
|
||||
*/
|
||||
const video = process.argv[2];
|
||||
const languages = process.argv[3]?.split(',');
|
||||
|
||||
|
||||
// Global Vars
|
||||
const subIndexes: number[] = [];
|
||||
let videoPath: string;
|
||||
let baseName: string;
|
||||
|
||||
|
||||
/**
|
||||
* Gets the relative path to the subtitle file of a ffmpeg stream.
|
||||
*
|
||||
* @param sub the stream of the subtitles to extract
|
||||
* @returns the path of the subtitle file
|
||||
*/
|
||||
const getSubPath = (sub: FfprobeStream): string => {
|
||||
const language = ISO6393To1.get(sub.tags.language);
|
||||
|
||||
const forced = sub.disposition?.forced === 0 ?
|
||||
'' :
|
||||
'.forced';
|
||||
|
||||
const hearingImpaired = sub.disposition?.hearing_impaired === 0 ?
|
||||
'' :
|
||||
'.sdh';
|
||||
|
||||
return `${baseName}${forced}.${language}${hearingImpaired}.srt`;
|
||||
};
|
||||
|
||||
/**
|
||||
* Removes all subtitles streams from the video file.
|
||||
*/
|
||||
const removeContainerSubs = (): void => {
|
||||
spawn('mv', [
|
||||
videoPath,
|
||||
`${videoPath}.bak`,
|
||||
], SPAWN_OPTS);
|
||||
|
||||
spawn('ffmpeg', [
|
||||
'-i', `${videoPath}.bak`,
|
||||
'-map', '0',
|
||||
...subIndexes.map((i) => ['-map', `-0:${i}`]).flat(),
|
||||
'-c', 'copy', videoPath,
|
||||
], SPAWN_OPTS);
|
||||
|
||||
spawn('rm', [
|
||||
`${videoPath}.bak`,
|
||||
], SPAWN_OPTS);
|
||||
};
|
||||
|
||||
/**
|
||||
* Extracts a sub of a video file to a subtitle file.
|
||||
*
|
||||
* @param sub the stream of the subtitles to extract
|
||||
*/
|
||||
const extractSub = (sub: FfprobeStream): void => {
|
||||
const subFile = getSubPath(sub);
|
||||
|
||||
spawn('ffmpeg', [
|
||||
'-i', videoPath,
|
||||
'-map', `0:${sub.index}`, subFile,
|
||||
], SPAWN_OPTS);
|
||||
|
||||
subIndexes.push(sub.index);
|
||||
};
|
||||
|
||||
/**
|
||||
* Sorts the list of streams to only keep subtitles
|
||||
* that can be extracted.
|
||||
*
|
||||
* @param lang the language of the subtitles
|
||||
* @param streams the streams
|
||||
* @returns the streams that represent subtitles
|
||||
*/
|
||||
const findSubs = (
|
||||
lang: string,
|
||||
streams: FfprobeStream[],
|
||||
): FfprobeStream[] => {
|
||||
const subs = streams.filter((s) => s.tags?.language &&
|
||||
s.tags.language === lang &&
|
||||
s.codec_type === 'subtitle');
|
||||
|
||||
const pgs = subs.filter((s) => s.codec_name === 'hdmv_pgs_subtitle');
|
||||
|
||||
// If we only have PGS subs, warn user
|
||||
if (pgs.length === subs.length) {
|
||||
console.warn(`No SRT subtitle tracks were found for ${lang}`);
|
||||
}
|
||||
|
||||
// Remove PGS streams from subs
|
||||
return subs.filter((s) => s.codec_name !== 'hdmv_pgs_subtitle');
|
||||
};
|
||||
|
||||
/**
|
||||
* Where the magic happens.
|
||||
*/
|
||||
const main = async(): Promise<void> => {
|
||||
// Get rid of video extension
|
||||
baseName = videoPath.split('/').at(-1)!.replace(/\.[^.]*$/, '');
|
||||
|
||||
// ffprobe the video file to see available sub tracks
|
||||
const data = await ffprobe(videoPath);
|
||||
|
||||
if (!data?.streams) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Check for languages wanted
|
||||
languages.forEach((lang) => {
|
||||
const subs = findSubs(lang, data.streams);
|
||||
|
||||
if (subs.length === 0) {
|
||||
console.warn(`No subtitle tracks were found for ${lang}`);
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
// Extract all subs
|
||||
subs.forEach((sub) => {
|
||||
extractSub(sub);
|
||||
});
|
||||
});
|
||||
|
||||
removeContainerSubs();
|
||||
};
|
||||
|
||||
|
||||
// Check if there are 2 params
|
||||
if (video && languages) {
|
||||
videoPath = video;
|
||||
main();
|
||||
}
|
||||
else {
|
||||
console.error('Error: no argument passed');
|
||||
process.exit(1);
|
||||
}
|
|
@ -1,8 +0,0 @@
|
|||
import Ffmpeg from 'fluent-ffmpeg';
|
||||
|
||||
|
||||
export default (videoPath: string) => new Promise<Ffmpeg.FfprobeData>((resolve) => {
|
||||
Ffmpeg.ffprobe(videoPath, (_e, data) => {
|
||||
resolve(data);
|
||||
});
|
||||
});
|
|
@ -1,373 +0,0 @@
|
|||
export const ISO6391To3 = new Map([
|
||||
['aa', 'aar'],
|
||||
['ab', 'abk'],
|
||||
['af', 'afr'],
|
||||
['ak', 'aka'],
|
||||
['am', 'amh'],
|
||||
['ar', 'ara'],
|
||||
['an', 'arg'],
|
||||
['as', 'asm'],
|
||||
['av', 'ava'],
|
||||
['ae', 'ave'],
|
||||
['ay', 'aym'],
|
||||
['az', 'aze'],
|
||||
['ba', 'bak'],
|
||||
['bm', 'bam'],
|
||||
['be', 'bel'],
|
||||
['bn', 'ben'],
|
||||
['bi', 'bis'],
|
||||
['bo', 'bod'],
|
||||
['bs', 'bos'],
|
||||
['br', 'bre'],
|
||||
['bg', 'bul'],
|
||||
['ca', 'cat'],
|
||||
['cs', 'ces'],
|
||||
['ch', 'cha'],
|
||||
['ce', 'che'],
|
||||
['cu', 'chu'],
|
||||
['cv', 'chv'],
|
||||
['kw', 'cor'],
|
||||
['co', 'cos'],
|
||||
['cr', 'cre'],
|
||||
['cy', 'cym'],
|
||||
['da', 'dan'],
|
||||
['de', 'deu'],
|
||||
['dv', 'div'],
|
||||
['dz', 'dzo'],
|
||||
['el', 'ell'],
|
||||
['en', 'eng'],
|
||||
['eo', 'epo'],
|
||||
['et', 'est'],
|
||||
['eu', 'eus'],
|
||||
['ee', 'ewe'],
|
||||
['fo', 'fao'],
|
||||
['fa', 'fas'],
|
||||
['fj', 'fij'],
|
||||
['fi', 'fin'],
|
||||
['fr', 'fre'],
|
||||
['fy', 'fry'],
|
||||
['ff', 'ful'],
|
||||
['gd', 'gla'],
|
||||
['ga', 'gle'],
|
||||
['gl', 'glg'],
|
||||
['gv', 'glv'],
|
||||
['gn', 'grn'],
|
||||
['gu', 'guj'],
|
||||
['ht', 'hat'],
|
||||
['ha', 'hau'],
|
||||
['sh', 'hbs'],
|
||||
['he', 'heb'],
|
||||
['hz', 'her'],
|
||||
['hi', 'hin'],
|
||||
['ho', 'hmo'],
|
||||
['hr', 'hrv'],
|
||||
['hu', 'hun'],
|
||||
['hy', 'hye'],
|
||||
['ig', 'ibo'],
|
||||
['io', 'ido'],
|
||||
['ii', 'iii'],
|
||||
['iu', 'iku'],
|
||||
['ie', 'ile'],
|
||||
['ia', 'ina'],
|
||||
['id', 'ind'],
|
||||
['ik', 'ipk'],
|
||||
['is', 'isl'],
|
||||
['it', 'ita'],
|
||||
['jv', 'jav'],
|
||||
['ja', 'jpn'],
|
||||
['kl', 'kal'],
|
||||
['kn', 'kan'],
|
||||
['ks', 'kas'],
|
||||
['ka', 'kat'],
|
||||
['kr', 'kau'],
|
||||
['kk', 'kaz'],
|
||||
['km', 'khm'],
|
||||
['ki', 'kik'],
|
||||
['rw', 'kin'],
|
||||
['ky', 'kir'],
|
||||
['kv', 'kom'],
|
||||
['kg', 'kon'],
|
||||
['ko', 'kor'],
|
||||
['kj', 'kua'],
|
||||
['ku', 'kur'],
|
||||
['lo', 'lao'],
|
||||
['la', 'lat'],
|
||||
['lv', 'lav'],
|
||||
['li', 'lim'],
|
||||
['ln', 'lin'],
|
||||
['lt', 'lit'],
|
||||
['lb', 'ltz'],
|
||||
['lu', 'lub'],
|
||||
['lg', 'lug'],
|
||||
['mh', 'mah'],
|
||||
['ml', 'mal'],
|
||||
['mr', 'mar'],
|
||||
['mk', 'mkd'],
|
||||
['mg', 'mlg'],
|
||||
['mt', 'mlt'],
|
||||
['mn', 'mon'],
|
||||
['mi', 'mri'],
|
||||
['ms', 'msa'],
|
||||
['my', 'mya'],
|
||||
['na', 'nau'],
|
||||
['nv', 'nav'],
|
||||
['nr', 'nbl'],
|
||||
['nd', 'nde'],
|
||||
['ng', 'ndo'],
|
||||
['ne', 'nep'],
|
||||
['nl', 'nld'],
|
||||
['nn', 'nno'],
|
||||
['nb', 'nob'],
|
||||
['no', 'nor'],
|
||||
['ny', 'nya'],
|
||||
['oc', 'oci'],
|
||||
['oj', 'oji'],
|
||||
['or', 'ori'],
|
||||
['om', 'orm'],
|
||||
['os', 'oss'],
|
||||
['pa', 'pan'],
|
||||
['pi', 'pli'],
|
||||
['pl', 'pol'],
|
||||
['pt', 'por'],
|
||||
['ps', 'pus'],
|
||||
['qu', 'que'],
|
||||
['rm', 'roh'],
|
||||
['ro', 'ron'],
|
||||
['rn', 'run'],
|
||||
['ru', 'rus'],
|
||||
['sg', 'sag'],
|
||||
['sa', 'san'],
|
||||
['si', 'sin'],
|
||||
['sk', 'slk'],
|
||||
['sl', 'slv'],
|
||||
['se', 'sme'],
|
||||
['sm', 'smo'],
|
||||
['sn', 'sna'],
|
||||
['sd', 'snd'],
|
||||
['so', 'som'],
|
||||
['st', 'sot'],
|
||||
['es', 'spa'],
|
||||
['sq', 'sqi'],
|
||||
['sc', 'srd'],
|
||||
['sr', 'srp'],
|
||||
['ss', 'ssw'],
|
||||
['su', 'sun'],
|
||||
['sw', 'swa'],
|
||||
['sv', 'swe'],
|
||||
['ty', 'tah'],
|
||||
['ta', 'tam'],
|
||||
['tt', 'tat'],
|
||||
['te', 'tel'],
|
||||
['tg', 'tgk'],
|
||||
['tl', 'tgl'],
|
||||
['th', 'tha'],
|
||||
['ti', 'tir'],
|
||||
['to', 'ton'],
|
||||
['tn', 'tsn'],
|
||||
['ts', 'tso'],
|
||||
['tk', 'tuk'],
|
||||
['tr', 'tur'],
|
||||
['tw', 'twi'],
|
||||
['ug', 'uig'],
|
||||
['uk', 'ukr'],
|
||||
['ur', 'urd'],
|
||||
['uz', 'uzb'],
|
||||
['ve', 'ven'],
|
||||
['vi', 'vie'],
|
||||
['vo', 'vol'],
|
||||
['wa', 'wln'],
|
||||
['wo', 'wol'],
|
||||
['xh', 'xho'],
|
||||
['yi', 'yid'],
|
||||
['yo', 'yor'],
|
||||
['za', 'zha'],
|
||||
['zh', 'zho'],
|
||||
['zu', 'zul'],
|
||||
]);
|
||||
|
||||
export const ISO6393To1 = new Map([
|
||||
['aar', 'aa'],
|
||||
['abk', 'ab'],
|
||||
['afr', 'af'],
|
||||
['aka', 'ak'],
|
||||
['amh', 'am'],
|
||||
['ara', 'ar'],
|
||||
['arg', 'an'],
|
||||
['asm', 'as'],
|
||||
['ava', 'av'],
|
||||
['ave', 'ae'],
|
||||
['aym', 'ay'],
|
||||
['aze', 'az'],
|
||||
['bak', 'ba'],
|
||||
['bam', 'bm'],
|
||||
['bel', 'be'],
|
||||
['ben', 'bn'],
|
||||
['bis', 'bi'],
|
||||
['bod', 'bo'],
|
||||
['bos', 'bs'],
|
||||
['bre', 'br'],
|
||||
['bul', 'bg'],
|
||||
['cat', 'ca'],
|
||||
['ces', 'cs'],
|
||||
['cha', 'ch'],
|
||||
['che', 'ce'],
|
||||
['chu', 'cu'],
|
||||
['chv', 'cv'],
|
||||
['cor', 'kw'],
|
||||
['cos', 'co'],
|
||||
['cre', 'cr'],
|
||||
['cym', 'cy'],
|
||||
['dan', 'da'],
|
||||
['deu', 'de'],
|
||||
['div', 'dv'],
|
||||
['dzo', 'dz'],
|
||||
['ell', 'el'],
|
||||
['eng', 'en'],
|
||||
['epo', 'eo'],
|
||||
['est', 'et'],
|
||||
['eus', 'eu'],
|
||||
['ewe', 'ee'],
|
||||
['fao', 'fo'],
|
||||
['fas', 'fa'],
|
||||
['fij', 'fj'],
|
||||
['fin', 'fi'],
|
||||
['fre', 'fr'],
|
||||
['fry', 'fy'],
|
||||
['ful', 'ff'],
|
||||
['gla', 'gd'],
|
||||
['gle', 'ga'],
|
||||
['glg', 'gl'],
|
||||
['glv', 'gv'],
|
||||
['grn', 'gn'],
|
||||
['guj', 'gu'],
|
||||
['hat', 'ht'],
|
||||
['hau', 'ha'],
|
||||
['hbs', 'sh'],
|
||||
['heb', 'he'],
|
||||
['her', 'hz'],
|
||||
['hin', 'hi'],
|
||||
['hmo', 'ho'],
|
||||
['hrv', 'hr'],
|
||||
['hun', 'hu'],
|
||||
['hye', 'hy'],
|
||||
['ibo', 'ig'],
|
||||
['ido', 'io'],
|
||||
['iii', 'ii'],
|
||||
['iku', 'iu'],
|
||||
['ile', 'ie'],
|
||||
['ina', 'ia'],
|
||||
['ind', 'id'],
|
||||
['ipk', 'ik'],
|
||||
['isl', 'is'],
|
||||
['ita', 'it'],
|
||||
['jav', 'jv'],
|
||||
['jpn', 'ja'],
|
||||
['kal', 'kl'],
|
||||
['kan', 'kn'],
|
||||
['kas', 'ks'],
|
||||
['kat', 'ka'],
|
||||
['kau', 'kr'],
|
||||
['kaz', 'kk'],
|
||||
['khm', 'km'],
|
||||
['kik', 'ki'],
|
||||
['kin', 'rw'],
|
||||
['kir', 'ky'],
|
||||
['kom', 'kv'],
|
||||
['kon', 'kg'],
|
||||
['kor', 'ko'],
|
||||
['kua', 'kj'],
|
||||
['kur', 'ku'],
|
||||
['lao', 'lo'],
|
||||
['lat', 'la'],
|
||||
['lav', 'lv'],
|
||||
['lim', 'li'],
|
||||
['lin', 'ln'],
|
||||
['lit', 'lt'],
|
||||
['ltz', 'lb'],
|
||||
['lub', 'lu'],
|
||||
['lug', 'lg'],
|
||||
['mah', 'mh'],
|
||||
['mal', 'ml'],
|
||||
['mar', 'mr'],
|
||||
['mkd', 'mk'],
|
||||
['mlg', 'mg'],
|
||||
['mlt', 'mt'],
|
||||
['mon', 'mn'],
|
||||
['mri', 'mi'],
|
||||
['msa', 'ms'],
|
||||
['mya', 'my'],
|
||||
['nau', 'na'],
|
||||
['nav', 'nv'],
|
||||
['nbl', 'nr'],
|
||||
['nde', 'nd'],
|
||||
['ndo', 'ng'],
|
||||
['nep', 'ne'],
|
||||
['nld', 'nl'],
|
||||
['nno', 'nn'],
|
||||
['nob', 'nb'],
|
||||
['nor', 'no'],
|
||||
['nya', 'ny'],
|
||||
['oci', 'oc'],
|
||||
['oji', 'oj'],
|
||||
['ori', 'or'],
|
||||
['orm', 'om'],
|
||||
['oss', 'os'],
|
||||
['pan', 'pa'],
|
||||
['pli', 'pi'],
|
||||
['pol', 'pl'],
|
||||
['por', 'pt'],
|
||||
['pus', 'ps'],
|
||||
['que', 'qu'],
|
||||
['roh', 'rm'],
|
||||
['ron', 'ro'],
|
||||
['run', 'rn'],
|
||||
['rus', 'ru'],
|
||||
['sag', 'sg'],
|
||||
['san', 'sa'],
|
||||
['sin', 'si'],
|
||||
['slk', 'sk'],
|
||||
['slv', 'sl'],
|
||||
['sme', 'se'],
|
||||
['smo', 'sm'],
|
||||
['sna', 'sn'],
|
||||
['snd', 'sd'],
|
||||
['som', 'so'],
|
||||
['sot', 'st'],
|
||||
['spa', 'es'],
|
||||
['sqi', 'sq'],
|
||||
['srd', 'sc'],
|
||||
['srp', 'sr'],
|
||||
['ssw', 'ss'],
|
||||
['sun', 'su'],
|
||||
['swa', 'sw'],
|
||||
['swe', 'sv'],
|
||||
['tah', 'ty'],
|
||||
['tam', 'ta'],
|
||||
['tat', 'tt'],
|
||||
['tel', 'te'],
|
||||
['tgk', 'tg'],
|
||||
['tgl', 'tl'],
|
||||
['tha', 'th'],
|
||||
['tir', 'ti'],
|
||||
['ton', 'to'],
|
||||
['tsn', 'tn'],
|
||||
['tso', 'ts'],
|
||||
['tuk', 'tk'],
|
||||
['tur', 'tr'],
|
||||
['twi', 'tw'],
|
||||
['uig', 'ug'],
|
||||
['ukr', 'uk'],
|
||||
['urd', 'ur'],
|
||||
['uzb', 'uz'],
|
||||
['ven', 've'],
|
||||
['vie', 'vi'],
|
||||
['vol', 'vo'],
|
||||
['wln', 'wa'],
|
||||
['wol', 'wo'],
|
||||
['xho', 'xh'],
|
||||
['yid', 'yi'],
|
||||
['yor', 'yo'],
|
||||
['zha', 'za'],
|
||||
['zho', 'zh'],
|
||||
['zul', 'zu'],
|
||||
]);
|
|
@ -1,10 +0,0 @@
|
|||
{
|
||||
"$schema": "https://json.schemastore.org/tsconfig",
|
||||
"extends": "../config/tsconfig.base.json",
|
||||
"includes": [
|
||||
"*.ts",
|
||||
"**/*.ts",
|
||||
"*.js",
|
||||
"**/*.js"
|
||||
]
|
||||
}
|
|
@ -1,15 +0,0 @@
|
|||
{
|
||||
writeShellApplication,
|
||||
jq,
|
||||
pandoc,
|
||||
...
|
||||
}:
|
||||
writeShellApplication {
|
||||
name = "gen-docs";
|
||||
runtimeInputs = [jq pandoc];
|
||||
text = builtins.readFile ./script.sh;
|
||||
|
||||
meta.description = ''
|
||||
Generates the READMEs in this repository from nix attributes.
|
||||
'';
|
||||
}
|
|
@ -1,13 +0,0 @@
|
|||
attr: selfPath: let
|
||||
inherit (builtins) mapAttrs replaceStrings;
|
||||
|
||||
modules = import "${selfPath}/${attr}" {description = true;};
|
||||
|
||||
trimNewlines = s: replaceStrings ["\n"] [" "] s;
|
||||
in {
|
||||
attrs =
|
||||
mapAttrs (_: v: {
|
||||
desc = trimNewlines v;
|
||||
})
|
||||
modules;
|
||||
}
|
|
@ -1,12 +0,0 @@
|
|||
configs: let
|
||||
inherit (builtins) mapAttrs replaceStrings;
|
||||
|
||||
trimNewlines = s: replaceStrings ["\n"] [" "] s;
|
||||
in {
|
||||
attrs =
|
||||
mapAttrs (_: v: {
|
||||
roleDesc = trimNewlines (v.config.meta.roleDescription or "");
|
||||
hwDesc = trimNewlines (v.config.meta.hardwareDescription or "");
|
||||
})
|
||||
configs;
|
||||
}
|
|
@ -1,13 +0,0 @@
|
|||
x: let
|
||||
inherit (builtins) currentSystem mapAttrs removeAttrs replaceStrings;
|
||||
|
||||
trimNewlines = s: replaceStrings ["\n"] [" "] s;
|
||||
packages = removeAttrs x.${currentSystem} ["default"];
|
||||
in {
|
||||
attrs =
|
||||
mapAttrs (_: v: {
|
||||
desc = trimNewlines (v.meta.description or "");
|
||||
homepage = v.meta.homepage or "";
|
||||
})
|
||||
packages;
|
||||
}
|
|
@ -1,31 +0,0 @@
|
|||
attr: selfPath: let
|
||||
inherit (builtins) currentSystem getFlake mapAttrs removeAttrs replaceStrings;
|
||||
|
||||
self = getFlake selfPath;
|
||||
scopes = import "${selfPath}/${attr}" {description = true;};
|
||||
|
||||
trimNewlines = s: replaceStrings ["\n"] [" "] s;
|
||||
in {
|
||||
attrs =
|
||||
mapAttrs (n: v: {
|
||||
desc = trimNewlines v;
|
||||
packages = let
|
||||
scopePkgs = removeAttrs self.${attr}.${currentSystem}.${n} [
|
||||
"buildFirefoxXpiAddon"
|
||||
"callPackage"
|
||||
"newScope"
|
||||
"override"
|
||||
"overrideDerivation"
|
||||
"overrideScope"
|
||||
"packages"
|
||||
"recurseForDerivations"
|
||||
];
|
||||
in
|
||||
mapAttrs (_: pkg: {
|
||||
desc = trimNewlines (pkg.meta.description or "");
|
||||
homepage = pkg.meta.homepage or "";
|
||||
})
|
||||
scopePkgs;
|
||||
})
|
||||
scopes;
|
||||
}
|
|
@ -1,43 +0,0 @@
|
|||
substituteDerivs() {
|
||||
echo '' | pandoc --metadata-file <(
|
||||
nix eval \
|
||||
--impure \
|
||||
--json \
|
||||
"$FLAKE"#"$1" \
|
||||
--apply "import \"$FLAKE/apps/gen-docs/$3.nix\"" |
|
||||
jq -r
|
||||
) -t markdown --template "$FLAKE/apps/gen-docs/templates/$2.md" -o "$FLAKE/$2/README.md"
|
||||
}
|
||||
|
||||
substituteAttrs() {
|
||||
echo '' | pandoc --metadata-file <(
|
||||
nix eval \
|
||||
--impure \
|
||||
--json \
|
||||
--expr "\"$FLAKE\"" \
|
||||
--apply "(import \"$FLAKE/apps/gen-docs/getAttrsMeta.nix\") \"$1\"" |
|
||||
jq -r
|
||||
) -t markdown --template "$FLAKE/apps/gen-docs/templates/$1.md" -o "$FLAKE/$1/README.md"
|
||||
}
|
||||
|
||||
substituteScopes() {
|
||||
echo '' | pandoc --metadata-file <(
|
||||
nix eval \
|
||||
--impure \
|
||||
--json \
|
||||
--expr "\"$FLAKE\"" \
|
||||
--apply "(import \"$FLAKE/apps/gen-docs/getScopesMeta.nix\") \"$1\"" |
|
||||
jq -r
|
||||
) -t markdown --template "$FLAKE/apps/gen-docs/templates/$1.md" -o "$FLAKE/$1/README.md"
|
||||
}
|
||||
|
||||
substituteDerivs "appsPackages" "apps" "getPackageMeta"
|
||||
substituteDerivs "nixosConfigurations" "configurations" "getConfigMeta"
|
||||
substituteDerivs "devShells" "devShells" "getPackageMeta"
|
||||
substituteDerivs "packages" "packages" "getPackageMeta"
|
||||
|
||||
substituteAttrs "modules"
|
||||
substituteAttrs "homeManagerModules"
|
||||
substituteAttrs "overlays"
|
||||
|
||||
substituteScopes "scopedPackages"
|
|
@ -1,11 +0,0 @@
|
|||
# Apps
|
||||
|
||||
This directory contains every derivations for apps exposed by this flake.
|
||||
|
||||
## List of my apps found in `self.apps`
|
||||
|
||||
| Name | Description |
|
||||
| ---- | ----------- |
|
||||
$for(attrs/pairs)$
|
||||
| `$it.key$` | $it.value.desc/nowrap$ |
|
||||
$endfor$
|
|
@ -1,13 +0,0 @@
|
|||
# NixosConfigurations
|
||||
|
||||
This directory contains every device's main configuration file, their `hardware-configuration.nix` and some custom modules
|
||||
unique to them.
|
||||
|
||||
## List of my devices
|
||||
|
||||
| Name | Model / Specs | Description |
|
||||
| --------- | ------------- | ------------------------------------------------------------------------------------------------ |
|
||||
| `android` | OnePlus 9 Pro | [Nix-On-Droid](https://github.com/nix-community/nix-on-droid) configuration for my OnePlus 9 Pro |
|
||||
$for(attrs/pairs)$
|
||||
| `$it.key$` | $it.value.hwDesc/nowrap$ | $it.value.roleDesc/nowrap$ |
|
||||
$endfor$
|
|
@ -1,11 +0,0 @@
|
|||
# DevShells
|
||||
|
||||
This directory contains every derivations for devShells exposed by this flake.
|
||||
|
||||
## List of my devShells found in `self.devShells`
|
||||
|
||||
| Name | Description |
|
||||
| ---- | ----------- |
|
||||
$for(attrs/pairs)$
|
||||
| `$it.key$` | $it.value.desc/nowrap$ |
|
||||
$endfor$
|
|
@ -1,11 +0,0 @@
|
|||
# HomeManagerModules
|
||||
|
||||
This directory contains every home-manager modules exposed by this flake.
|
||||
|
||||
## List of my home-manager modules found in `self.homeManagerModules`
|
||||
|
||||
| Name | Description |
|
||||
| ---- | ----------- |
|
||||
$for(attrs/pairs)$
|
||||
| `$it.key$` | $it.value.desc/nowrap$ |
|
||||
$endfor$
|
|
@ -1,11 +0,0 @@
|
|||
# NixosModules
|
||||
|
||||
This directory contains every modules for NixOS exposed by this flake.
|
||||
|
||||
## List of my modules found in `self.nixosModules`
|
||||
|
||||
| Name | Description |
|
||||
| ---- | ----------- |
|
||||
$for(attrs/pairs)$
|
||||
| `$it.key$` | $it.value.desc/nowrap$ |
|
||||
$endfor$
|
|
@ -1,11 +0,0 @@
|
|||
# Overlays
|
||||
|
||||
This directory contains every overlay exposed by this flake.
|
||||
|
||||
## List of my overlays found in `self.overlays`
|
||||
|
||||
| Name | Description |
|
||||
| ---- | ----------- |
|
||||
$for(attrs/pairs)$
|
||||
| `$it.key$` | $it.value.desc/nowrap$ |
|
||||
$endfor$
|
|
@ -1,11 +0,0 @@
|
|||
# Packages
|
||||
|
||||
This directory contains every derivations for packages exposed by this flake.
|
||||
|
||||
## List of my packages found in `self.packages`
|
||||
|
||||
| Name | Description | Homepage |
|
||||
| ---- | ----------- | -------- |
|
||||
$for(attrs/pairs)$
|
||||
| `$it.key$` | $it.value.desc/nowrap$ | $it.value.homepage/nowrap$ |
|
||||
$endfor$
|
|
@ -1,18 +0,0 @@
|
|||
# ScopedPackages
|
||||
|
||||
This directory contains every package scopes exposed by this flake.
|
||||
|
||||
## List of my package scopes found in `self.scopedPackages`
|
||||
|
||||
$for(attrs/pairs)$
|
||||
### $it.key$
|
||||
|
||||
$it.value.desc/nowrap$
|
||||
|
||||
| Name | Description | Homepage |
|
||||
| ---- | ----------- | -------- |
|
||||
$for(it.value.packages/pairs)$
|
||||
| `$it.key$` | $it.value.desc/nowrap$ | $it.value.homepage/nowrap$ |
|
||||
$endfor$
|
||||
|
||||
$endfor$
|
|
@ -1,16 +0,0 @@
|
|||
{
|
||||
inputs,
|
||||
pkgs,
|
||||
...
|
||||
}: let
|
||||
inherit (pkgs.lib) listToAttrs nameValuePair;
|
||||
|
||||
buildApp = attrs: (pkgs.callPackage ./buildApp.nix ({} // inputs // attrs));
|
||||
callPackage = file: pkgs.callPackage file ({inherit buildApp;} // inputs);
|
||||
in
|
||||
listToAttrs (map (x: nameValuePair x (callPackage ./${x})) [
|
||||
"extract-subs"
|
||||
"gen-docs"
|
||||
"pin-inputs"
|
||||
"update-sources"
|
||||
])
|
|
@ -1,3 +0,0 @@
|
|||
use flake $FLAKE#node
|
||||
(cd ../config; npm ci)
|
||||
npm ci
|
|
@ -1,11 +0,0 @@
|
|||
{buildApp, ...}:
|
||||
buildApp {
|
||||
src = ./.;
|
||||
npmDepsHash = "sha256-qNTgtT+x1O1jMWYgs8pXy3fUJKHBnf9adhR9nD5V7TY=";
|
||||
|
||||
runtimeInputs = [];
|
||||
|
||||
meta.description = ''
|
||||
Takes a list of inputs to pin to their current rev in `flake.lock`.
|
||||
'';
|
||||
}
|
|
@ -1,3 +0,0 @@
|
|||
import eslintConf from 'eslint-conf';
|
||||
|
||||
export default eslintConf;
|
1653
apps/pin-inputs/package-lock.json
generated
1653
apps/pin-inputs/package-lock.json
generated
File diff suppressed because it is too large
Load diff
|
@ -1,18 +0,0 @@
|
|||
{
|
||||
"name": "pin-inputs",
|
||||
"version": "0.0.0",
|
||||
"bin": "out/bin/app.cjs",
|
||||
"type": "module",
|
||||
"scripts": {
|
||||
"build": "node_ver=$(node -v); esbuild src/app.ts --bundle --platform=node --target=\"node${node_ver:1:2}\" --outfile=out/bin/app.cjs"
|
||||
},
|
||||
"devDependencies": {
|
||||
"eslint-conf": "file:../config",
|
||||
"@types/node": "22.12.0",
|
||||
"esbuild": "0.24.2",
|
||||
"eslint": "9.19.0",
|
||||
"jiti": "2.4.2",
|
||||
"pkg-types": "1.3.1",
|
||||
"typescript": "5.7.3"
|
||||
}
|
||||
}
|
|
@ -1,62 +0,0 @@
|
|||
import { readFileSync, writeFileSync } from 'fs';
|
||||
|
||||
export const replaceInFile = (replace: RegExp, replacement: string, file: string) => {
|
||||
const fileContents = readFileSync(file);
|
||||
|
||||
const replaced = fileContents.toString().replace(replace, replacement);
|
||||
|
||||
writeFileSync(file, replaced);
|
||||
};
|
||||
|
||||
/* Constants */
|
||||
const FLAKE = process.env.FLAKE;
|
||||
|
||||
if (!FLAKE) {
|
||||
console.error('Environment variable FLAKE not found');
|
||||
process.exit(1);
|
||||
}
|
||||
|
||||
const FLAKE_LOCK = JSON.parse(readFileSync(`${FLAKE}/flake.lock`, 'utf8')).nodes;
|
||||
const INPUT_REVS = new Map<string, string>();
|
||||
|
||||
Object.entries(FLAKE_LOCK).forEach(([key, val]) => {
|
||||
if (key !== 'root') {
|
||||
// eslint-disable-next-line
|
||||
INPUT_REVS.set(key, (val as any).locked.rev);
|
||||
}
|
||||
});
|
||||
|
||||
const INPUTS = process.argv.slice(2);
|
||||
|
||||
|
||||
/**
|
||||
* Gets the commit hash of the specified input in this flake.
|
||||
*
|
||||
* @param input the name of the input
|
||||
* @returns the commit hash
|
||||
*/
|
||||
const getCurrentRev = (input: string): string => {
|
||||
if (!INPUT_REVS.has(input)) {
|
||||
throw new Error(`Input ${input} could not be found.`);
|
||||
}
|
||||
|
||||
return INPUT_REVS.get(input) as string;
|
||||
};
|
||||
|
||||
INPUTS.forEach((input) => {
|
||||
try {
|
||||
const inputsFile = `${FLAKE}/inputs/default.nix`;
|
||||
const rev = getCurrentRev(input);
|
||||
|
||||
const msg = ['FIX', 'ME'].join('');
|
||||
|
||||
replaceInFile(
|
||||
new RegExp(`(\\n[ ]*)${input} =.*\\n.*\\n.*`),
|
||||
`$&\n$1 # ${msg}: $1 rev = "${rev}";`,
|
||||
inputsFile,
|
||||
);
|
||||
}
|
||||
catch (e) {
|
||||
console.error((e as Error).message);
|
||||
}
|
||||
});
|
|
@ -1,10 +0,0 @@
|
|||
{
|
||||
"$schema": "https://json.schemastore.org/tsconfig",
|
||||
"extends": "../config/tsconfig.base.json",
|
||||
"includes": [
|
||||
"*.ts",
|
||||
"**/*.ts",
|
||||
"*.js",
|
||||
"**/*.js"
|
||||
]
|
||||
}
|
|
@ -1,3 +0,0 @@
|
|||
use flake $FLAKE#node
|
||||
(cd ../config; npm ci)
|
||||
npm ci
|
|
@ -1,32 +0,0 @@
|
|||
{
|
||||
buildApp,
|
||||
callPackage,
|
||||
curl,
|
||||
findutils,
|
||||
go,
|
||||
jq,
|
||||
nix-update,
|
||||
nodejs_latest,
|
||||
prefetch-npm-deps,
|
||||
...
|
||||
}:
|
||||
buildApp {
|
||||
src = ./.;
|
||||
npmDepsHash = "sha256-2cWxVTCOEJOg2eBv+xX/mvr6MUX+UJQ8JlkoObD6+Uc=";
|
||||
|
||||
runtimeInputs = [
|
||||
curl
|
||||
findutils
|
||||
go
|
||||
jq
|
||||
nix-update
|
||||
nodejs_latest
|
||||
prefetch-npm-deps
|
||||
(callPackage ../../modules/docker/updateImage.nix {})
|
||||
];
|
||||
|
||||
meta.description = ''
|
||||
Updates all derivation sources in this repository and
|
||||
generates a commit message for the changes made.
|
||||
'';
|
||||
}
|
|
@ -1,3 +0,0 @@
|
|||
import eslintConf from 'eslint-conf';
|
||||
|
||||
export default eslintConf;
|
1666
apps/update-sources/package-lock.json
generated
1666
apps/update-sources/package-lock.json
generated
File diff suppressed because it is too large
Load diff
|
@ -1,18 +0,0 @@
|
|||
{
|
||||
"name": "update-sources",
|
||||
"version": "0.0.0",
|
||||
"bin": "out/bin/app.cjs",
|
||||
"type": "module",
|
||||
"scripts": {
|
||||
"build": "node_ver=$(node -v); esbuild src/app.ts --bundle --platform=node --target=\"node${node_ver:1:2}\" --outfile=out/bin/app.cjs"
|
||||
},
|
||||
"devDependencies": {
|
||||
"eslint-conf": "file:../config",
|
||||
"@types/node": "22.13.4",
|
||||
"esbuild": "0.25.0",
|
||||
"eslint": "9.20.1",
|
||||
"jiti": "2.4.2",
|
||||
"pkg-types": "1.3.1",
|
||||
"typescript": "5.7.3"
|
||||
}
|
||||
}
|
|
@ -1,188 +0,0 @@
|
|||
import { spawnSync } from 'node:child_process';
|
||||
import { writeFileSync } from 'node:fs';
|
||||
|
||||
import { parseArgs } from './lib';
|
||||
|
||||
import { updateDocker } from './docker';
|
||||
import { updateFirefoxAddons } from '././firefox';
|
||||
import { updateFlakeInputs } from './flake';
|
||||
import updateNodeModules from './node-modules';
|
||||
|
||||
import {
|
||||
runNixUpdate,
|
||||
updateCaddyPlugins,
|
||||
updateVuetorrent,
|
||||
} from './misc';
|
||||
|
||||
|
||||
/* Constants */
|
||||
const FLAKE = process.env.FLAKE;
|
||||
|
||||
if (!FLAKE) {
|
||||
console.error('Env var FLAKE not found');
|
||||
process.exit(1);
|
||||
}
|
||||
|
||||
const args = parseArgs();
|
||||
|
||||
const main = async() => {
|
||||
if (args['c'] || args['custom-sidebar']) {
|
||||
console.log(runNixUpdate('scopedPackages', 'lovelace-components', 'custom-sidebar'));
|
||||
}
|
||||
|
||||
if (args['cp'] || args['caddy-plugins']) {
|
||||
console.log(updateCaddyPlugins());
|
||||
}
|
||||
|
||||
if (args['d'] || args['docker']) {
|
||||
console.log(updateDocker());
|
||||
}
|
||||
|
||||
if (args['f'] || args['firefox']) {
|
||||
console.log(updateFirefoxAddons());
|
||||
}
|
||||
|
||||
if (args['h'] || args['homepage']) {
|
||||
console.log(runNixUpdate('homepage'));
|
||||
}
|
||||
|
||||
if (args['i'] || args['inputs']) {
|
||||
console.log(updateFlakeInputs());
|
||||
}
|
||||
|
||||
if (args['j'] || args['jmusicbot']) {
|
||||
console.log(runNixUpdate('jmusicbot'));
|
||||
}
|
||||
|
||||
if (args['m'] || args['material-rounded-theme']) {
|
||||
console.log(runNixUpdate('scopedPackages', 'lovelace-components', 'material-rounded-theme'));
|
||||
}
|
||||
|
||||
if (args['n'] || args['node_modules']) {
|
||||
console.log(await updateNodeModules());
|
||||
}
|
||||
|
||||
if (args['p'] || args['pam-fprint-grosshack']) {
|
||||
console.log(runNixUpdate('pam-fprint-grosshack'));
|
||||
}
|
||||
|
||||
if (args['ph'] || args['protonhax']) {
|
||||
console.log(runNixUpdate('protonhax'));
|
||||
}
|
||||
|
||||
if (args['s'] || args['some-sass-language-server']) {
|
||||
console.log(runNixUpdate('some-sass-language-server'));
|
||||
}
|
||||
|
||||
if (args['t'] || args['trash-d']) {
|
||||
console.log(runNixUpdate('trash-d'));
|
||||
}
|
||||
|
||||
if (args['v'] || args['vuetorrent']) {
|
||||
console.log(updateVuetorrent());
|
||||
}
|
||||
|
||||
if (args['a'] || args['all']) {
|
||||
// Update this first because of nix run cmd
|
||||
const firefoxOutput = updateFirefoxAddons();
|
||||
|
||||
console.log(firefoxOutput);
|
||||
|
||||
|
||||
const flakeOutput = updateFlakeInputs();
|
||||
|
||||
console.log(flakeOutput);
|
||||
|
||||
|
||||
const dockerOutput = updateDocker();
|
||||
|
||||
console.log(dockerOutput);
|
||||
|
||||
|
||||
const nodeModulesOutput = await updateNodeModules();
|
||||
|
||||
console.log(nodeModulesOutput);
|
||||
|
||||
|
||||
const vuetorrentOutput = updateVuetorrent();
|
||||
|
||||
console.log(vuetorrentOutput);
|
||||
|
||||
|
||||
const caddyPluginsOutput = updateCaddyPlugins();
|
||||
|
||||
console.log(caddyPluginsOutput);
|
||||
|
||||
|
||||
// nix-update executions
|
||||
let nixUpdateOutputs = '';
|
||||
|
||||
const updatePackage = (
|
||||
attr: string,
|
||||
scope?: string,
|
||||
scopeAttr?: string,
|
||||
): void => {
|
||||
const execution = runNixUpdate(attr, scope, scopeAttr);
|
||||
|
||||
nixUpdateOutputs += execution.stdout;
|
||||
console.log(execution.stderr);
|
||||
console.log(execution.stdout);
|
||||
};
|
||||
|
||||
updatePackage('homepage');
|
||||
updatePackage('jmusicbot');
|
||||
updatePackage('pam-fprint-grosshack');
|
||||
updatePackage('protonhax');
|
||||
updatePackage('some-sass-language-server');
|
||||
updatePackage('trash-d');
|
||||
updatePackage('scopedPackages', 'lovelace-components', 'custom-sidebar');
|
||||
updatePackage('scopedPackages', 'lovelace-components', 'material-rounded-theme');
|
||||
|
||||
|
||||
spawnSync('nixFastBuild', [], {
|
||||
shell: true,
|
||||
stdio: [process.stdin, process.stdout, process.stderr],
|
||||
});
|
||||
|
||||
const indentOutput = (output: string): string => {
|
||||
return ` ${output.split('\n').join('\n ')}`;
|
||||
};
|
||||
|
||||
const output = [
|
||||
'chore: update sources\n\n',
|
||||
];
|
||||
|
||||
if (flakeOutput.length > 5) {
|
||||
output.push(`Flake Inputs:\n${indentOutput(flakeOutput)}\n\n`);
|
||||
}
|
||||
if (dockerOutput.length > 5) {
|
||||
output.push(`Docker Images:\n${indentOutput(dockerOutput)}\n`);
|
||||
}
|
||||
if (firefoxOutput.length > 5) {
|
||||
output.push(`Firefox Addons:\n${indentOutput(firefoxOutput)}\n\n`);
|
||||
}
|
||||
if (nodeModulesOutput.length > 5) {
|
||||
output.push(`Node modules:\n${indentOutput(nodeModulesOutput)}\n`);
|
||||
}
|
||||
if (vuetorrentOutput.length > 5) {
|
||||
output.push(`Misc Sources:\n${indentOutput(vuetorrentOutput)}\n\n`);
|
||||
}
|
||||
if (caddyPluginsOutput.length > 5) {
|
||||
output.push(`Caddy Plugins:\n${indentOutput(caddyPluginsOutput)}\n\n`);
|
||||
}
|
||||
if (nixUpdateOutputs.length > 5) {
|
||||
output.push(`nix-update executions:\n${indentOutput(nixUpdateOutputs)}\n`);
|
||||
}
|
||||
|
||||
if (args['f']) {
|
||||
writeFileSync(args['f'] as string, output.join(''));
|
||||
}
|
||||
else {
|
||||
console.log(output.join(''));
|
||||
}
|
||||
}
|
||||
|
||||
spawnSync('alejandra', ['-q', FLAKE], { shell: true });
|
||||
};
|
||||
|
||||
main();
|
|
@ -1,33 +0,0 @@
|
|||
import { readdirSync } from 'node:fs';
|
||||
import { spawnSync } from 'node:child_process';
|
||||
|
||||
|
||||
/* Constants */
|
||||
const FLAKE = process.env.FLAKE;
|
||||
|
||||
const updateImages = (imagePath: string): string | undefined => {
|
||||
console.log(`Updating ${imagePath.split('/').at(-1)} images`);
|
||||
|
||||
const out = spawnSync('updateImages', [imagePath], { shell: true }).stdout.toString();
|
||||
|
||||
if (!out.startsWith('# Locked')) {
|
||||
return out;
|
||||
}
|
||||
};
|
||||
|
||||
export const updateDocker = () => {
|
||||
let updates = '';
|
||||
|
||||
updates += updateImages(`${FLAKE}/configurations/nos/modules/jellyfin`) ?? '';
|
||||
updates += updateImages(`${FLAKE}/configurations/homie/modules/home-assistant/netdaemon`) ?? '';
|
||||
|
||||
const DIR = `${FLAKE}/configurations/nos/modules/docker`;
|
||||
|
||||
readdirSync(DIR, { withFileTypes: true, recursive: true }).forEach((path) => {
|
||||
if (path.name === 'compose.nix') {
|
||||
updates += updateImages(path.parentPath) ?? '';
|
||||
}
|
||||
});
|
||||
|
||||
return updates;
|
||||
};
|
|
@ -1,61 +0,0 @@
|
|||
import { spawnSync } from 'node:child_process';
|
||||
import { readFileSync } from 'node:fs';
|
||||
|
||||
|
||||
/* Constants */
|
||||
const FLAKE = process.env.FLAKE;
|
||||
|
||||
export const updateFirefoxAddons = () => {
|
||||
console.log('Updating firefox addons using mozilla-addons-to-nix');
|
||||
|
||||
const DIR = `${FLAKE}/scopedPackages/firefox-addons`;
|
||||
const GENERATED_FILE = `${DIR}/generated-firefox-addons.nix`;
|
||||
const SLUGS = `${DIR}/addons.json`;
|
||||
|
||||
const nameMap = Object.fromEntries([...JSON.parse(readFileSync(SLUGS, 'utf-8'))]
|
||||
.map((addon) => [addon.slug, addon.pname || addon.slug]));
|
||||
|
||||
const nixExpr = `'
|
||||
x: let
|
||||
inherit (builtins) attrValues filter hasAttr isAttrs map;
|
||||
in
|
||||
map (d: d.name) (filter (y:
|
||||
isAttrs y &&
|
||||
hasAttr "type" y &&
|
||||
y.type == "derivation") (attrValues x))
|
||||
'`;
|
||||
|
||||
const OLD_VERS = Object.fromEntries([...JSON.parse(spawnSync('nix', [
|
||||
'eval',
|
||||
'.#scopedPackages.x86_64-linux.firefoxAddons',
|
||||
'--apply',
|
||||
nixExpr,
|
||||
'--json',
|
||||
], { shell: true }).stdout.toString())]
|
||||
.map((p) => {
|
||||
const pname = p.replace(/-[0-9].*$/, '');
|
||||
|
||||
return [pname, p.replace(`${pname}-`, '')];
|
||||
})
|
||||
.filter((pinfo) => pinfo[0] !== 'frankerfacez'));
|
||||
|
||||
const NEW_VERS = Object.fromEntries(spawnSync(
|
||||
'nix',
|
||||
['run', 'sourcehut:~rycee/mozilla-addons-to-nix',
|
||||
SLUGS, GENERATED_FILE],
|
||||
{ shell: true },
|
||||
).stdout
|
||||
.toString()
|
||||
.split('\n')
|
||||
.map((p) => {
|
||||
const pinfo = p.replace('Fetched ', '').split(' ');
|
||||
|
||||
return [nameMap[pinfo[0]], pinfo[2]];
|
||||
}));
|
||||
|
||||
return Object.keys(OLD_VERS)
|
||||
.sort()
|
||||
.filter((pname) => OLD_VERS[pname] !== NEW_VERS[pname])
|
||||
.map((pname) => `${pname}: ${OLD_VERS[pname]} -> ${NEW_VERS[pname]}`)
|
||||
.join('\n');
|
||||
};
|
|
@ -1,45 +0,0 @@
|
|||
import { spawnSync } from 'node:child_process';
|
||||
|
||||
|
||||
/* Constants */
|
||||
const FLAKE = process.env.FLAKE;
|
||||
|
||||
export const updateFlakeInputs = () => {
|
||||
const output = spawnSync(
|
||||
`git restore flake.lock &> /dev/null; nix flake update --flake ${FLAKE}` +
|
||||
' |& grep -v "warning: updating lock file" |& grep -v "unpacking"',
|
||||
[],
|
||||
{ shell: true },
|
||||
).stdout
|
||||
.toString()
|
||||
// Add an extra blank line between inputs
|
||||
.split('\n•')
|
||||
// Filter out some inputs
|
||||
.filter((input) => ![
|
||||
'systems',
|
||||
'flake-compat',
|
||||
'flake-utils',
|
||||
'flake-parts',
|
||||
'treefmt-nix',
|
||||
'lib-aggregate',
|
||||
'lib-aggregate/nixpkgs-lib',
|
||||
'nix-gaming/umu',
|
||||
'nix-github-actions',
|
||||
'pre-commit-hooks',
|
||||
].some((inputName) => input.startsWith(` Updated input '${inputName}'`)))
|
||||
.join('\n\n•')
|
||||
// help readability of git revs
|
||||
.split('\n')
|
||||
.map((l) => l
|
||||
.replace(
|
||||
/\/(.{40})\?narHash=sha256[^']*(.*)/,
|
||||
(_, backref1, backref2) => `${backref2} rev: ${backref1}`,
|
||||
)
|
||||
.replace(
|
||||
/\?ref.*&rev=(.{40})[^'&]*(.*)/,
|
||||
(_, backref1, backref2) => `${backref2} rev: ${backref1}`,
|
||||
))
|
||||
.join('\n');
|
||||
|
||||
return output;
|
||||
};
|
|
@ -1,43 +0,0 @@
|
|||
import { spawnSync } from 'node:child_process';
|
||||
import { readFileSync, writeFileSync } from 'node:fs';
|
||||
|
||||
|
||||
export const parseArgs = () => {
|
||||
const args = {} as Record<string, unknown>;
|
||||
let lastFlag: string | null = null;
|
||||
|
||||
for (let i = 2; i < process.argv.length; ++i) {
|
||||
const arg = process.argv[i];
|
||||
|
||||
if (arg.toString().startsWith('-')) {
|
||||
lastFlag = arg.toString().replace(/^-{1,2}/, '');
|
||||
args[lastFlag] = true;
|
||||
}
|
||||
else if (lastFlag) {
|
||||
args[lastFlag] = arg;
|
||||
lastFlag = null;
|
||||
}
|
||||
else {
|
||||
console.error(`Could not parse args: ${arg.toString()}`);
|
||||
}
|
||||
}
|
||||
|
||||
return args;
|
||||
};
|
||||
|
||||
export const parseFetchurl = (url: string) => JSON.parse(spawnSync(
|
||||
'nix', ['store', 'prefetch-file', '--refresh', '--json',
|
||||
'--hash-type', 'sha256', url, '--name', '"escaped"'], { shell: true },
|
||||
).stdout.toString()).hash;
|
||||
|
||||
export const replaceInFile = (replace: RegExp, replacement: string, file: string) => {
|
||||
const fileContents = readFileSync(file);
|
||||
|
||||
const replaced = fileContents.toString().replace(replace, replacement);
|
||||
|
||||
writeFileSync(file, replaced);
|
||||
};
|
||||
|
||||
export const npmRun = (args: string[], workspaceDir: string) => spawnSync(
|
||||
'npm', args, { cwd: workspaceDir },
|
||||
).stdout.toString();
|
|
@ -1,161 +0,0 @@
|
|||
import { writeFileSync } from 'node:fs';
|
||||
import { spawnSync } from 'node:child_process';
|
||||
|
||||
import { parseFetchurl, replaceInFile } from './lib';
|
||||
|
||||
|
||||
/* Constants */
|
||||
const FLAKE = process.env.FLAKE;
|
||||
|
||||
const genVueText = (
|
||||
version: string,
|
||||
hash: string,
|
||||
url: string,
|
||||
) => `# This file was autogenerated. DO NOT EDIT!
|
||||
{
|
||||
version = "${version}";
|
||||
url = "${url}";
|
||||
hash = "${hash}";
|
||||
}
|
||||
`;
|
||||
|
||||
export const updateVuetorrent = () => {
|
||||
const FILE = `${FLAKE}/configurations/nos/modules/qbittorrent/vuetorrent.nix`;
|
||||
|
||||
const OLD_VERSION = JSON.parse(spawnSync('nix',
|
||||
['eval', '-f', FILE, '--json'],
|
||||
{ shell: true }).stdout.toString()).version;
|
||||
|
||||
const VERSION = JSON.parse(spawnSync('curl',
|
||||
['-s', 'https://api.github.com/repos/VueTorrent/VueTorrent/releases/latest'],
|
||||
{ shell: true }).stdout.toString()).tag_name.replace('v', '');
|
||||
|
||||
const URL = `https://github.com/VueTorrent/VueTorrent/releases/download/v${VERSION}/vuetorrent.zip`;
|
||||
const HASH = parseFetchurl(URL);
|
||||
|
||||
const fileText = genVueText(VERSION, HASH, URL);
|
||||
|
||||
writeFileSync(FILE, fileText);
|
||||
|
||||
return OLD_VERSION !== VERSION ? `Vuetorrent: ${OLD_VERSION} -> ${VERSION}` : '';
|
||||
};
|
||||
|
||||
|
||||
const getAttrVersion = (attr: string): string => spawnSync('nix',
|
||||
['eval', '--raw', `${FLAKE}#${attr}.version`],
|
||||
{ shell: true }).stdout.toString();
|
||||
|
||||
export const runNixUpdate = (
|
||||
attr: string,
|
||||
scope?: string,
|
||||
scopeAttr?: string,
|
||||
): { stdout: string, stderr: string } => {
|
||||
const getJsonArray = (jsonObj: string) => Array(JSON.parse(jsonObj))[0].slice(1).join(' ');
|
||||
|
||||
const realAttr = scope ? `${attr}.x86_64-linux.${scope}.${scopeAttr}` : attr;
|
||||
const OLD_VERSION = getAttrVersion(realAttr);
|
||||
|
||||
const execOptions = spawnSync(
|
||||
`nix eval --json ${FLAKE}#${realAttr}.updateScript`,
|
||||
[],
|
||||
{ shell: true, cwd: FLAKE },
|
||||
);
|
||||
|
||||
const options = execOptions.status === 0 ?
|
||||
execOptions.stdout.toString().startsWith('[') ?
|
||||
getJsonArray(execOptions.stdout.toString()) :
|
||||
'-u' :
|
||||
'';
|
||||
|
||||
const execution = spawnSync(
|
||||
`nix-update --flake ${realAttr} ${options} --write-commit-message >(head -n 1 -) > /dev/null`,
|
||||
[],
|
||||
{ shell: true, cwd: FLAKE },
|
||||
);
|
||||
|
||||
const NEW_VERSION = getAttrVersion(realAttr);
|
||||
|
||||
return {
|
||||
stdout: OLD_VERSION !== NEW_VERSION ?
|
||||
scope ?
|
||||
execution.stdout.toString().replaceAll(`${attr}.x86_64-linux.${scope}.`, '') :
|
||||
execution.stdout.toString() :
|
||||
'',
|
||||
stderr: execution.stderr.toString(),
|
||||
};
|
||||
};
|
||||
|
||||
|
||||
const genPluginsText = (
|
||||
plugins: Record<string, { url: string, version: string }>,
|
||||
) => `# This file was autogenerated. DO NOT EDIT!
|
||||
{
|
||||
plugins = {
|
||||
${Object.entries(plugins)
|
||||
.map(([key, value]) => `
|
||||
${key} = {
|
||||
url = "${value.url}";
|
||||
version = "${value.version}";
|
||||
};
|
||||
`)
|
||||
.join('')}
|
||||
};
|
||||
|
||||
hash = "";
|
||||
}
|
||||
`;
|
||||
|
||||
export const updateCaddyPlugins = () => {
|
||||
let updates = '';
|
||||
const dir = `${FLAKE}/configurations/cluster/modules/caddy`;
|
||||
|
||||
// Setup workspace
|
||||
spawnSync(
|
||||
[
|
||||
'rm -rf /tmp/update-caddy',
|
||||
'mkdir -p /tmp/update-caddy',
|
||||
'cd /tmp/update-caddy || exit 1',
|
||||
'go mod init temp',
|
||||
].join('; '),
|
||||
[],
|
||||
{ shell: true, cwd: '/tmp' },
|
||||
);
|
||||
|
||||
const plugins = JSON.parse(spawnSync('nix',
|
||||
['eval', '-f', `${dir}/plugins.nix`, '--json'],
|
||||
{ shell: true }).stdout.toString()).plugins as Record<string, { url: string, version: string }>;
|
||||
|
||||
// Get most recent versions of plugins
|
||||
Object.entries(plugins).forEach(([key, value]) => {
|
||||
const NEW_VERSION = spawnSync([
|
||||
'go mod init temp > /dev/null',
|
||||
`go get ${value.url} > /dev/null`,
|
||||
`grep '${value.url}' go.mod`,
|
||||
].join('; '), [], { shell: true, cwd: '/tmp/update-caddy' })
|
||||
.stdout
|
||||
.toString()
|
||||
.trim()
|
||||
.replace(' // indirect', '')
|
||||
.split(' ')[1];
|
||||
|
||||
if (plugins[key].version !== NEW_VERSION) {
|
||||
updates += `${key}: ${plugins[key].version} -> ${NEW_VERSION}`;
|
||||
plugins[key].version = NEW_VERSION;
|
||||
}
|
||||
});
|
||||
|
||||
writeFileSync(`${dir}/plugins.nix`, genPluginsText(plugins));
|
||||
|
||||
// Get new hash
|
||||
const caddyPkgAttr = 'nixosConfigurations.thingone.config.services.caddy.package';
|
||||
|
||||
const NEW_HASH = spawnSync(
|
||||
`nix build "$FLAKE#${caddyPkgAttr}" |& sed -n 's/.*got: *//p'`,
|
||||
[],
|
||||
{ shell: true },
|
||||
).stdout.toString().trim();
|
||||
|
||||
replaceInFile(/hash = ".*";/, `hash = "${NEW_HASH}";`, `${dir}/plugins.nix`);
|
||||
|
||||
return updates;
|
||||
};
|
|
@ -1,103 +0,0 @@
|
|||
import { readPackageJSON, writePackageJSON } from 'pkg-types';
|
||||
import { accessSync, constants, existsSync } from 'node:fs';
|
||||
import { spawnSync } from 'node:child_process';
|
||||
|
||||
import { replaceInFile, npmRun } from './lib';
|
||||
|
||||
|
||||
/* Constants */
|
||||
const FLAKE = process.env.FLAKE as string;
|
||||
|
||||
|
||||
const updatePackageJson = async(workspaceDir: string, updates: object) => {
|
||||
const currentPackageJson = await readPackageJSON(`${workspaceDir}/package.json`);
|
||||
|
||||
const outdated = JSON.parse(npmRun(['outdated', '--json'], workspaceDir));
|
||||
|
||||
const updateDeps = (deps: string) => {
|
||||
Object.keys(currentPackageJson[deps]).forEach((dep) => {
|
||||
const versions = outdated[dep];
|
||||
const current = versions?.wanted || versions?.current;
|
||||
|
||||
if (!current) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (current !== versions.latest) {
|
||||
updates[dep] = `${current} -> ${versions.latest}`;
|
||||
}
|
||||
|
||||
currentPackageJson[deps][dep] = versions.latest;
|
||||
});
|
||||
};
|
||||
|
||||
if (currentPackageJson.dependencies) {
|
||||
updateDeps('dependencies');
|
||||
}
|
||||
|
||||
if (currentPackageJson.devDependencies) {
|
||||
updateDeps('devDependencies');
|
||||
}
|
||||
|
||||
await writePackageJSON(`${workspaceDir}/package.json`, currentPackageJson);
|
||||
};
|
||||
|
||||
|
||||
const prefetchNpmDeps = (workspaceDir: string): string => {
|
||||
npmRun(['update', '--package-lock-only'], workspaceDir);
|
||||
|
||||
return spawnSync(
|
||||
'prefetch-npm-deps',
|
||||
[`${workspaceDir}/package-lock.json`],
|
||||
).stdout.toString().replace('\n', '');
|
||||
};
|
||||
|
||||
|
||||
export default async() => {
|
||||
console.log('Updating node modules');
|
||||
|
||||
const updates = {};
|
||||
|
||||
const packages = spawnSync('find', [FLAKE, '-name', 'package.json']).stdout.toString().split('\n')
|
||||
.filter((f) => f !== '')
|
||||
.filter((f) => ![
|
||||
'.direnv',
|
||||
'node_modules',
|
||||
'results',
|
||||
].some((dirName) => f.includes(dirName)));
|
||||
|
||||
for (const path of packages) {
|
||||
console.log(path);
|
||||
|
||||
try {
|
||||
accessSync(path, constants.R_OK | constants.W_OK);
|
||||
|
||||
const parentPath = path.replace('/package.json', '');
|
||||
|
||||
await updatePackageJson(parentPath, updates);
|
||||
|
||||
if (existsSync(`${parentPath}/default.nix`)) {
|
||||
const hash = prefetchNpmDeps(parentPath);
|
||||
|
||||
replaceInFile(
|
||||
/npmDepsHash = ".*";/,
|
||||
`npmDepsHash = "${hash}";`,
|
||||
`${parentPath}/default.nix`,
|
||||
);
|
||||
}
|
||||
|
||||
// Make sure we update the apps' config package-lock.json
|
||||
if (parentPath.includes('apps/config')) {
|
||||
npmRun(['i'], parentPath);
|
||||
}
|
||||
}
|
||||
catch (e) {
|
||||
console.warn(`Could not write to ${path}`);
|
||||
console.warn(e);
|
||||
}
|
||||
}
|
||||
|
||||
return Object.entries(updates)
|
||||
.map(([key, dep]) => `${key}: ${dep}`)
|
||||
.join('\n');
|
||||
};
|
|
@ -1,10 +0,0 @@
|
|||
{
|
||||
"$schema": "https://json.schemastore.org/tsconfig",
|
||||
"extends": "../config/tsconfig.base.json",
|
||||
"includes": [
|
||||
"*.ts",
|
||||
"**/*.ts",
|
||||
"*.js",
|
||||
"**/*.js"
|
||||
]
|
||||
}
|
1
config/eww/README.md
Normal file
1
config/eww/README.md
Normal file
|
@ -0,0 +1 @@
|
|||
inspired from: https://github.com/AlphaTechnolog/dotfiles/tree/openbox
|
1
config/eww/closer/README.md
Normal file
1
config/eww/closer/README.md
Normal file
|
@ -0,0 +1 @@
|
|||
always open this widget last
|
60
config/eww/closer/closer.yuck
Normal file
60
config/eww/closer/closer.yuck
Normal file
|
@ -0,0 +1,60 @@
|
|||
(defwidget closer []
|
||||
(eventbox :onclick "$EWW_PATH/close-opened.sh && eww close closer")
|
||||
)
|
||||
(defwindow closer :monitor 0
|
||||
:geometry (geometry :width "100%"
|
||||
:height "100%")
|
||||
:stacking "overlay"
|
||||
:focusable false
|
||||
(closer :window "")
|
||||
)
|
||||
|
||||
(defwidget closer-notif []
|
||||
(eventbox :onclick "$EWW_PATH/notif-toggle.sh off")
|
||||
)
|
||||
(defwindow closer-notif1 :monitor 0
|
||||
:geometry (geometry :width "1360px"
|
||||
:height "1200px")
|
||||
:stacking "overlay"
|
||||
:focusable false
|
||||
:exclusive "ignore"
|
||||
(closer-notif)
|
||||
)
|
||||
(defwindow closer-notif2 :monitor 0
|
||||
:geometry (geometry :width "100%"
|
||||
:height "200px"
|
||||
:y "1060px")
|
||||
:stacking "overlay"
|
||||
:focusable false
|
||||
:exclusive "ignore"
|
||||
(closer-notif)
|
||||
)
|
||||
(defwindow closer-notif3 :monitor 0
|
||||
:geometry (geometry :width "100%"
|
||||
:height "60px")
|
||||
:stacking "overlay"
|
||||
:focusable false
|
||||
:exclusive "ignore"
|
||||
(closer-notif)
|
||||
)
|
||||
(defwindow closer-notif4 :monitor 0
|
||||
:geometry (geometry :width "60px"
|
||||
:height "100%"
|
||||
:x "1860px")
|
||||
:stacking "overlay"
|
||||
:focusable false
|
||||
:exclusive "ignore"
|
||||
(closer-notif)
|
||||
)
|
||||
|
||||
(defwidget on-release-fix []
|
||||
(eventbox :onclick "eww close on-release-fix")
|
||||
)
|
||||
(defwindow on-release-fix :monitor 0
|
||||
:geometry (geometry :width "100%"
|
||||
:height "100%"
|
||||
)
|
||||
:stacking "overlay"
|
||||
:exclusive "ignore"
|
||||
(on-release-fix)
|
||||
)
|
32
config/eww/colors.scss
Normal file
32
config/eww/colors.scss
Normal file
|
@ -0,0 +1,32 @@
|
|||
$darkbg: #0b0d16;
|
||||
$bg: rgba(40, 42, 54, 0.8); //rgba(69, 71, 90, 0.3); #0d0f18;
|
||||
$bgfull: rgb(40, 42, 54);
|
||||
$contrastbg: rgba(189, 147, 249, 0.8);
|
||||
$bgSecondary: #11131c;
|
||||
$bgSecondaryAlt: #a5b6cf;
|
||||
$fg: #a5b6cf;
|
||||
$fgDim: #a5b6cf;
|
||||
$watermelon: #dd6777;
|
||||
|
||||
// Aliases
|
||||
$background: $bg;
|
||||
$backgroundSecondary: $bgSecondary;
|
||||
$backgroundSecondaryAlt: $bgSecondaryAlt;
|
||||
$foreground: $fg;
|
||||
$foregroundDim: $fgDim;
|
||||
|
||||
$black: #151720;
|
||||
$dimblack: #1a1c25;
|
||||
$lightblack: #262831;
|
||||
$red: #dd6777;
|
||||
$blue: #86aaec;
|
||||
$cyan: #93cee9;
|
||||
$blue-desaturated: #93cee9;
|
||||
$magenta: #c296eb;
|
||||
$purple: #c296eb;
|
||||
$green: #90ceaa;
|
||||
$aquamarine: #90ceaa;
|
||||
$yellow: #ecd3a0;
|
||||
$accent: $blue;
|
||||
$javacafeMagenta: #c296eb;
|
||||
$javacafeBlue: #86aaec;
|
75
config/eww/date/date.scss
Normal file
75
config/eww/date/date.scss
Normal file
|
@ -0,0 +1,75 @@
|
|||
.date {
|
||||
background-color: $bg;
|
||||
color: $fg;
|
||||
border-radius: 30px;
|
||||
border: 2px solid $contrastbg;
|
||||
}
|
||||
|
||||
.timebox {
|
||||
margin: 30px 0px;
|
||||
.time-container {
|
||||
.content {
|
||||
font-family: Product Sans;
|
||||
font-weight: bolder;
|
||||
font-size: 60px;
|
||||
}
|
||||
.divider {
|
||||
margin: 8px 15px;
|
||||
padding: 0px 1px;
|
||||
background: linear-gradient($red, $magenta, $blue, $cyan);
|
||||
}
|
||||
}
|
||||
.date-container {
|
||||
font-family: Product Sans;
|
||||
margin-top: 2px;
|
||||
}
|
||||
}
|
||||
|
||||
.cal-box {
|
||||
font-family: Product Sans;
|
||||
background-color: $bg;
|
||||
border-radius: 30px;
|
||||
padding: 0 1rem .2rem;
|
||||
color: $fg;
|
||||
background-color: $bgfull;
|
||||
border-bottom: 2px solid $contrastbg;
|
||||
border-top: 2px solid $contrastbg;
|
||||
margin: 0px 12px 18px 12px;
|
||||
|
||||
.cal {
|
||||
background-color: inherit;
|
||||
padding: .5rem .10rem 0rem;
|
||||
margin-left: 10px;
|
||||
border-radius: 30px;
|
||||
|
||||
& > * {
|
||||
border: solid 0px transparent;
|
||||
}
|
||||
|
||||
&.highlight {
|
||||
padding: 10rem;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
calendar:selected {
|
||||
color: $cyan;
|
||||
}
|
||||
|
||||
calendar.header {
|
||||
color: $cyan;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
calendar.button {
|
||||
color: $cyan;
|
||||
}
|
||||
|
||||
calendar.highlight {
|
||||
color: $green;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
calendar:indeterminate {
|
||||
color: $lightblack;
|
||||
}
|
63
config/eww/date/date.yuck
Normal file
63
config/eww/date/date.yuck
Normal file
|
@ -0,0 +1,63 @@
|
|||
(defwidget divider []
|
||||
(box :class "divider"
|
||||
:orientation "v"
|
||||
:space-evenly true)
|
||||
)
|
||||
|
||||
(defwidget time []
|
||||
(box :class "timebox"
|
||||
:orientation "v"
|
||||
:space-evenly false
|
||||
(box :class "time-container"
|
||||
:orientation "h"
|
||||
:space-evenly false
|
||||
:halign "center"
|
||||
:valign "center"
|
||||
(label :text "${lithour}" :class "content")
|
||||
(divider)
|
||||
(label :text "${litmin}" :class "content")
|
||||
)
|
||||
(box :class "date-container"
|
||||
:orientation "h"
|
||||
:space-evenly true
|
||||
:halign "center"
|
||||
(label :text "${completeday}")
|
||||
)
|
||||
)
|
||||
)
|
||||
|
||||
(defwidget cal []
|
||||
(box :class "cal-box"
|
||||
:orientation "v"
|
||||
:space-evenly false
|
||||
(calendar :class "cal"
|
||||
:day calendar_day
|
||||
:month calendar_month
|
||||
:year calendar_year)
|
||||
)
|
||||
)
|
||||
|
||||
(defwidget date []
|
||||
(box :class "date"
|
||||
:orientation "v"
|
||||
:space-evenly false
|
||||
(time)
|
||||
(cal)
|
||||
)
|
||||
)
|
||||
|
||||
(defvar date-visible false)
|
||||
|
||||
(defwindow date-reveal
|
||||
:monitor 0
|
||||
:stacking "overlay"
|
||||
:geometry (geometry :x "70px"
|
||||
:y "8px"
|
||||
:width "0px" ; automatically generated
|
||||
:height "0px" ; automatically generated
|
||||
:anchor "top right")
|
||||
(revealer
|
||||
:transition "crossfade"
|
||||
:reveal date-visible
|
||||
:duration anim_duration
|
||||
(date)))
|
10
config/eww/eww.scss
Normal file
10
config/eww/eww.scss
Normal file
|
@ -0,0 +1,10 @@
|
|||
* {
|
||||
all: unset;
|
||||
}
|
||||
|
||||
@import "colors.scss";
|
||||
@import "date/date.scss";
|
||||
@import "powermenu/powermenu.scss";
|
||||
@import "playerinfo/playerinfo.scss";
|
||||
@import "quick-settings/quick-settings.scss";
|
||||
@import "traybuttons/traybuttons.scss";
|
7
config/eww/eww.yuck
Normal file
7
config/eww/eww.yuck
Normal file
|
@ -0,0 +1,7 @@
|
|||
(include "variables.yuck")
|
||||
(include "date/date.yuck")
|
||||
(include "powermenu/powermenu.yuck")
|
||||
(include "playerinfo/playerinfo.yuck")
|
||||
(include "closer/closer.yuck")
|
||||
(include "quick-settings/quick-settings.yuck")
|
||||
(include "traybuttons/traybuttons.yuck")
|
90
config/eww/playerinfo/playerinfo.scss
Normal file
90
config/eww/playerinfo/playerinfo.scss
Normal file
|
@ -0,0 +1,90 @@
|
|||
.playerinfo {
|
||||
padding: 10px;
|
||||
min-width: 400px;
|
||||
border-radius: 30px;
|
||||
border-top: 2px solid $contrastbg;
|
||||
border-bottom: 2px solid $contrastbg;
|
||||
transition: background 250ms;
|
||||
.top {
|
||||
font-size: 23px;
|
||||
}
|
||||
.metadata {
|
||||
.title{
|
||||
font-weight: 500;
|
||||
transition: text 250ms;
|
||||
}
|
||||
.artist{
|
||||
font-weight: 400;
|
||||
font-size: 15px;
|
||||
transition: text 250ms;
|
||||
}
|
||||
}
|
||||
.bottom {
|
||||
font-size: 30px;
|
||||
}
|
||||
|
||||
.pausebutton {
|
||||
transition: background 250ms;
|
||||
padding: 14px 16px;
|
||||
font-size: 15px;
|
||||
}
|
||||
|
||||
.playing {
|
||||
transition: all ease .2s;
|
||||
border-radius: 15px;
|
||||
label {
|
||||
padding-left: 4px;
|
||||
}
|
||||
}
|
||||
|
||||
.paused {
|
||||
border-radius: 26px;
|
||||
transition: all ease .2s;
|
||||
padding: 14px 14px 14px 18px;
|
||||
}
|
||||
}
|
||||
|
||||
.previousbutton,
|
||||
.nextbutton,
|
||||
.shuffle,
|
||||
.repeat {
|
||||
border-radius: 100%;
|
||||
transition: background-color 200ms;
|
||||
&:hover {
|
||||
border-radius: 100%;
|
||||
background-color: rgba(127, 132, 156, 0.4);
|
||||
transition: background-color 200ms;
|
||||
}
|
||||
}
|
||||
|
||||
.repeat {
|
||||
label {
|
||||
padding-right: 8px;
|
||||
}
|
||||
}
|
||||
|
||||
.song-pos {
|
||||
scale {
|
||||
highlight {
|
||||
margin: 0px;
|
||||
border-radius: 2em;
|
||||
}
|
||||
|
||||
trough {
|
||||
background-color: #363847;
|
||||
border-radius: 2em;
|
||||
}
|
||||
|
||||
slider {
|
||||
margin: -8px;
|
||||
min-height: 20px;
|
||||
border-radius: 10px;
|
||||
box-shadow: rgba(0, 0, 0, 0.25) 0px 54px 55px, rgba(0, 0, 0, 0.12) 0px -12px 30px, rgba(0, 0, 0, 0.12) 0px 4px 6px, rgba(0, 0, 0, 0.17) 0px 12px 13px, rgba(0, 0, 0, 0.09) 0px -3px 5px;
|
||||
transition: background-color 0.5s ease-in-out;
|
||||
}
|
||||
slider:hover {
|
||||
background-color: #303240;
|
||||
transition: background-color 0.5s ease-in-out;
|
||||
}
|
||||
}
|
||||
}
|
124
config/eww/playerinfo/playerinfo.yuck
Normal file
124
config/eww/playerinfo/playerinfo.yuck
Normal file
|
@ -0,0 +1,124 @@
|
|||
(defpoll player :interval "1s" "echo Spot")
|
||||
(defpoll music_cover :interval "1s" "$EWW_PATH/music.sh cover") ;done
|
||||
(defvar music_accent "rgb(0,0,0)") ;done
|
||||
(defvar button_accent "rgb(0,0,0)") ;done
|
||||
(defvar button_text "rgb(255,255,255)") ;done
|
||||
(defpoll music_status :interval "1s" "playerctl -p Spot status")
|
||||
(defpoll title :interval "1s" "playerctl -p Spot metadata title")
|
||||
(defpoll artist :interval "1s" "playerctl -p Spot metadata artist")
|
||||
(defvar button_height "42")
|
||||
(defpoll shuffle_status :interval "1s" "playerctl -p Spot shuffle")
|
||||
(defpoll repeat_icon :interval "1s" "$EWW_PATH/music.sh loop_status")
|
||||
(defvar song_pos "0")
|
||||
(defpoll song_length :interval "1s" "$EWW_PATH/music.sh length")
|
||||
(defvar get_pos "true")
|
||||
|
||||
(defwidget playerinfo []
|
||||
(centerbox :class "playerinfo"
|
||||
:style "background: radial-gradient(circle, rgba(0, 0, 0, 0.4) 30%, ${music_accent}), url(\"${music_cover}\");
|
||||
background-size: cover;
|
||||
background-position: center;"
|
||||
:orientation "v"
|
||||
(box :class "top"
|
||||
:halign "start"
|
||||
:valign "start"
|
||||
:style "color: ${button_accent};"
|
||||
"${player == 'Spot' ? '' : '爵' }"
|
||||
)
|
||||
(box :class "center"
|
||||
:orientation "h"
|
||||
:space-evenly false
|
||||
(box :class "metadata"
|
||||
:orientation "v"
|
||||
:halign "start"
|
||||
:valign "center"
|
||||
:hexpand true
|
||||
(label :limit-width 25 :halign "start" :text title :class "title")
|
||||
(label :limit-width 25 :halign "start" :text artist :class "artist")
|
||||
)
|
||||
(centerbox :orientation "v"
|
||||
(label)
|
||||
(eventbox :class "pausebutton ${music_status == 'Playing' ? 'playing' : 'paused'}"
|
||||
:halign "left"
|
||||
:style "background-color: ${button_accent};
|
||||
color: ${button_text};"
|
||||
:onclick "playerctl -p Spot play-pause"
|
||||
:cursor "pointer"
|
||||
:onhover "eww update button_height=41"
|
||||
:onhoverlost "eww update button_height=42"
|
||||
|
||||
(label :text "${music_status == 'Playing' ? ' ' : ''}"
|
||||
:width button_height
|
||||
:height button_height
|
||||
)
|
||||
)
|
||||
(label)
|
||||
)
|
||||
)
|
||||
(box :class "bottom"
|
||||
:style "color: ${button_accent};"
|
||||
:space-evenly false
|
||||
:spacing 0
|
||||
(eventbox :valign "end"
|
||||
:halign "start"
|
||||
:onclick "playerctl -p Spot previous & $EWW_PATH/music.sh cover"
|
||||
:class "previousbutton"
|
||||
:width 40
|
||||
:cursor "pointer"
|
||||
""
|
||||
)
|
||||
(eventbox :cursor "pointer"
|
||||
:class "song-pos"
|
||||
:hexpand true
|
||||
:onhover "eww update get_pos=false"
|
||||
:onhoverlost "eww update get_pos=true"
|
||||
(scale :value song_pos
|
||||
:min 0
|
||||
:max song_length
|
||||
:orientation "h"
|
||||
:onchange "playerctl -p Spot position {}"
|
||||
:css "highlight { background-color: ${button_accent}; }
|
||||
slider { background-color: ${button_accent}; }
|
||||
trough { background-color: rgba(${button_accent}, 0.4); }"
|
||||
)
|
||||
)
|
||||
(box :valign "end"
|
||||
:halign "end"
|
||||
|
||||
(eventbox :onclick "playerctl -p Spot next & $EWW_PATH/music.sh cover"
|
||||
:class "nextbutton"
|
||||
:width 40
|
||||
:cursor "pointer"
|
||||
""
|
||||
)
|
||||
(eventbox :onclick "playerctl -p Spot shuffle toggle"
|
||||
:class "shuffle"
|
||||
:width 40
|
||||
:cursor "pointer"
|
||||
"${shuffle_status == 'On' ? '' : ''}"
|
||||
)
|
||||
(eventbox :onclick "$EWW_PATH/music.sh loop"
|
||||
:class "repeat"
|
||||
:width 40
|
||||
:cursor "pointer"
|
||||
"${repeat_icon}"
|
||||
)
|
||||
)
|
||||
)
|
||||
)
|
||||
)
|
||||
(defwindow playerinfo
|
||||
:monitor 0
|
||||
:stacking "overlay"
|
||||
:exclusive "ignore"
|
||||
:focusable "false"
|
||||
:geometry (geometry :x "800px"
|
||||
:y "10px"
|
||||
:width "0px"
|
||||
:height "0px"
|
||||
:anchor "top left"
|
||||
)
|
||||
(playerinfo)
|
||||
)
|
||||
|
||||
|
28
config/eww/powermenu/powermenu.scss
Normal file
28
config/eww/powermenu/powermenu.scss
Normal file
|
@ -0,0 +1,28 @@
|
|||
.powermenu {
|
||||
background-color: $bg;
|
||||
color: $fg;
|
||||
padding: 20px;
|
||||
font-family: MesloLGS NF;
|
||||
/*font-family: Iosevka Nerd Font;*/
|
||||
font-size: 70px;
|
||||
border-radius: 30px;
|
||||
border: 2px solid $contrastbg;
|
||||
button {
|
||||
border-radius: 12px;
|
||||
min-width: 80px;
|
||||
transition: all ease .2s;
|
||||
&:hover { background-color: $bgSecondary; }
|
||||
&:active { background-color: $bgSecondary; }
|
||||
.content {
|
||||
border-radius: 4px;
|
||||
padding: 0px 15px 0px 15px;
|
||||
}
|
||||
}
|
||||
.shutdown { color: $red; }
|
||||
.reboot { color: $magenta; }
|
||||
.logout { color: $yellow; }
|
||||
}
|
||||
|
||||
.powermenu-clickhandler {
|
||||
background-color: black;
|
||||
}
|
55
config/eww/powermenu/powermenu.yuck
Normal file
55
config/eww/powermenu/powermenu.yuck
Normal file
|
@ -0,0 +1,55 @@
|
|||
(defwidget powermenu []
|
||||
(box :class "powermenu"
|
||||
:orientation "h"
|
||||
:space-evenly true
|
||||
:spacing 20
|
||||
(button :class "shutdown"
|
||||
:onclick "systemctl poweroff"
|
||||
(label :text "襤" :class "content")
|
||||
)
|
||||
(button :class "reboot"
|
||||
:onclick "systemctl reboot"
|
||||
(label :text "勒" :class "content")
|
||||
)
|
||||
(button :class "logout"
|
||||
:onclick "hyprctl dispatch exit"
|
||||
(label :text "" :class "content")
|
||||
)
|
||||
)
|
||||
)
|
||||
|
||||
(defwidget powermenu-clickhandler []
|
||||
(button :class "powermenu-clickhandler"
|
||||
:onclick "eww close powermenu powermenu-clickhandler"
|
||||
""
|
||||
)
|
||||
)
|
||||
|
||||
(defwindow powermenu-clickhandler
|
||||
:monitor 0
|
||||
:geometry (geometry :x "0px"
|
||||
:y "0px"
|
||||
:width "100%"
|
||||
:height "100%"
|
||||
:anchor "center")
|
||||
:wm-ignore true
|
||||
(powermenu-clickhandler)
|
||||
)
|
||||
|
||||
(defvar powermenu-visible false)
|
||||
|
||||
(defwindow powermenu-reveal
|
||||
:monitor 0
|
||||
:stacking "overlay"
|
||||
:geometry (geometry :x "0px"
|
||||
:y "0px"
|
||||
:width "500px"
|
||||
:height "150px"
|
||||
:anchor "center")
|
||||
(revealer
|
||||
:transition "crossfade"
|
||||
:reveal powermenu-visible
|
||||
:duration anim_duration
|
||||
(powermenu)
|
||||
)
|
||||
)
|
190
config/eww/quick-settings/quick-settings.scss
Normal file
190
config/eww/quick-settings/quick-settings.scss
Normal file
|
@ -0,0 +1,190 @@
|
|||
.quick-settings-smol {
|
||||
font-size: 2px;
|
||||
min-height: 52px;
|
||||
min-width: 36px;
|
||||
padding: 0px 0px 0px 0px;
|
||||
background-color: $bg;
|
||||
color: rgba(0,0,0,0);
|
||||
border: 2px solid $contrastbg;
|
||||
border-bottom: none;
|
||||
border-top-right-radius: 80px;
|
||||
border-top-left-radius: 80px;
|
||||
border-bottom-left-radius: 0px;
|
||||
border-bottom-right-radius: 0px;
|
||||
}
|
||||
|
||||
.quick-settings-logo {
|
||||
font-size: 24px;
|
||||
min-height: 36px;
|
||||
min-width: 36px;
|
||||
padding: 0px 0px 0px 0px;
|
||||
background-color: rgba(0,0,0,0);
|
||||
color: #CBA6F7;
|
||||
border-radius: 80px;
|
||||
border: 2px solid rgba(0,0,0,0);
|
||||
transition: background-color 0.5s ease-in-out;
|
||||
}
|
||||
|
||||
.quick-settings-logo:hover, .quick-settings-logo:active {
|
||||
background-color: rgba(127, 132, 156, 0.4);
|
||||
transition: background-color 0.5s ease-in-out;
|
||||
}
|
||||
|
||||
.quick-settings {
|
||||
font-size: 30px;
|
||||
min-width: 500px;
|
||||
padding: 0px 0px 0px 0px;
|
||||
background-color: $bg;
|
||||
border-top-right-radius: 0px;
|
||||
border-top-left-radius: 30px;
|
||||
border-bottom-left-radius: 30px;
|
||||
border-bottom-right-radius: 30px;
|
||||
border: 2px solid $contrastbg;
|
||||
}
|
||||
|
||||
.title {
|
||||
font-size: 22px;
|
||||
margin-top: 30px;
|
||||
}
|
||||
|
||||
.grid-label {
|
||||
font-size: 30px;
|
||||
margin-left: 15px;
|
||||
margin-right: 10px;
|
||||
min-width: 50px;
|
||||
}
|
||||
|
||||
.sub-label {
|
||||
font-size: 14px;
|
||||
margin-top: -10px;
|
||||
margin-left: 0px;
|
||||
margin-bottom: 10px;
|
||||
padding: 3px;
|
||||
border: 2px solid $contrastbg;
|
||||
border-top-right-radius: 20px;
|
||||
border-top-left-radius: 10px;
|
||||
border-bottom-left-radius: 10px;
|
||||
border-bottom-right-radius: 20px;
|
||||
min-width: 106px;
|
||||
background: #1b1b1b;
|
||||
}
|
||||
|
||||
.grid-chev {
|
||||
margin-left: 0px;
|
||||
|
||||
font-size: 40px;
|
||||
margin-right: 5px;
|
||||
}
|
||||
|
||||
.button-grid {
|
||||
font-size: 10px;
|
||||
min-height: 160px;
|
||||
min-width: 470px;
|
||||
background-color: $bgfull;
|
||||
border-top: 2px solid $contrastbg;
|
||||
border-bottom: 2px solid $contrastbg;
|
||||
border-radius: 15px;
|
||||
margin-top: 30px;
|
||||
}
|
||||
|
||||
.button-row {
|
||||
min-height: 70px;
|
||||
min-width: 450px;
|
||||
margin-left: 20px;
|
||||
}
|
||||
|
||||
.grid-button {
|
||||
min-height: 65px;
|
||||
min-width: 70px;
|
||||
margin: 5px;
|
||||
}
|
||||
|
||||
.left-part {
|
||||
background: #1b1b1b;
|
||||
border-top-left-radius: 15px;
|
||||
border-bottom-left-radius: 15px;
|
||||
border-left: 2px solid $contrastbg;
|
||||
border-top: 2px solid $contrastbg;
|
||||
border-bottom: 2px solid $contrastbg;
|
||||
transition: all 0.5s ease-in-out;
|
||||
}
|
||||
|
||||
.right-part {
|
||||
background: #1b1b1b;
|
||||
border-top-right-radius: 30px;
|
||||
border-bottom-right-radius: 30px;
|
||||
border-right: 2px solid $contrastbg;
|
||||
border-top: 2px solid $contrastbg;
|
||||
border-bottom: 2px solid $contrastbg;
|
||||
transition: all 0.5s ease-in-out;
|
||||
}
|
||||
|
||||
.right-part:hover, .right-part:active {
|
||||
color: $contrastbg;
|
||||
border: 2px solid $contrastbg;
|
||||
border-top-left-radius: 7px;
|
||||
border-bottom-left-radius: 7px;
|
||||
transition: all 0.5s ease-in-out;
|
||||
}
|
||||
|
||||
.left-part:hover, .left-part:active {
|
||||
color: $contrastbg;
|
||||
border: 2px solid $contrastbg;
|
||||
border-top-right-radius: 7px;
|
||||
border-bottom-right-radius: 7px;
|
||||
transition: all 0.5s ease-in-out;
|
||||
}
|
||||
|
||||
.player {
|
||||
margin-top: 6px;
|
||||
min-height: 220px;
|
||||
opacity: 0;
|
||||
}
|
||||
|
||||
.slider-box {
|
||||
min-height: 100px;
|
||||
min-width: 470px;
|
||||
background-color: $bgfull;
|
||||
border-top: 2px solid $contrastbg;
|
||||
border-bottom: 2px solid $contrastbg;
|
||||
border-radius: 15px;
|
||||
margin-top: 30px;
|
||||
margin-bottom: 20px;
|
||||
|
||||
.slider-label {
|
||||
font-size: 30px;
|
||||
min-width: 30px;
|
||||
}
|
||||
|
||||
scale {
|
||||
min-height: 55px;
|
||||
min-width: 400px;
|
||||
margin-left: 18px;
|
||||
margin-right: 20px;
|
||||
|
||||
highlight {
|
||||
margin: 0px;
|
||||
background-color: #79659f;
|
||||
border-radius: 2em;
|
||||
}
|
||||
|
||||
trough {
|
||||
background-color: #363847;
|
||||
border-radius: 2em;
|
||||
}
|
||||
|
||||
slider {
|
||||
margin: -4px;
|
||||
min-width: 20px;
|
||||
min-height: 20px;
|
||||
background: #3e4153;
|
||||
border-radius: 100%;
|
||||
box-shadow: rgba(0, 0, 0, 0.25) 0px 54px 55px, rgba(0, 0, 0, 0.12) 0px -12px 30px, rgba(0, 0, 0, 0.12) 0px 4px 6px, rgba(0, 0, 0, 0.17) 0px 12px 13px, rgba(0, 0, 0, 0.09) 0px -3px 5px;
|
||||
transition: background-color 0.5s ease-in-out;
|
||||
}
|
||||
slider:hover {
|
||||
background-color: #303240;
|
||||
transition: background-color 0.5s ease-in-out;
|
||||
}
|
||||
}
|
||||
}
|
360
config/eww/quick-settings/quick-settings.yuck
Normal file
360
config/eww/quick-settings/quick-settings.yuck
Normal file
|
@ -0,0 +1,360 @@
|
|||
(defvar showqs false)
|
||||
(defvar showplayer false)
|
||||
|
||||
(defwidget quick-settings-smol []
|
||||
(box :class "quick-settings-smol"
|
||||
:orientation "h"
|
||||
(label :text " ")
|
||||
)
|
||||
)
|
||||
(defwindow quick-settings-smol-reveal
|
||||
:monitor 0
|
||||
:stacking "overlay"
|
||||
:exclusive "ignore"
|
||||
:geometry (geometry :x "5px"
|
||||
:y "10px"
|
||||
:width "0px"
|
||||
:height "0px"
|
||||
:anchor "top right"
|
||||
)
|
||||
(revealer
|
||||
:transition "crossfade"
|
||||
:reveal showqs
|
||||
:duration anim_duration
|
||||
(quick-settings-smol)
|
||||
)
|
||||
)
|
||||
|
||||
(defvar qs-run-off "false")
|
||||
(defwidget quick-settings-logo []
|
||||
(eventbox :class "quick-settings-logo"
|
||||
:onclick "$EWW_PATH/run.sh '$EWW_PATH/qs-toggle.sh off' qs-run-off &"
|
||||
:cursor "pointer"
|
||||
:onhover "eww update qs-run-off=true"
|
||||
:onhoverlost "eww update qs-run-off=false"
|
||||
|
||||
(box :class "quick-settings-logo"
|
||||
:orientation "h"
|
||||
(label :text " ")
|
||||
)
|
||||
)
|
||||
)
|
||||
(defwindow quick-settings-logo-reveal
|
||||
:monitor 0
|
||||
:stacking "overlay"
|
||||
:exclusive "ignore"
|
||||
:geometry (geometry :x "5px"
|
||||
:y "10px"
|
||||
:width "0px"
|
||||
:height "0px"
|
||||
:anchor "top right"
|
||||
)
|
||||
(revealer
|
||||
:transition "crossfade"
|
||||
:reveal showqs
|
||||
:duration anim_duration
|
||||
(quick-settings-logo)
|
||||
)
|
||||
)
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
(defvar expand_player "false")
|
||||
(defwidget quick-settings []
|
||||
(box :orientation "v"
|
||||
:space-evenly false
|
||||
(box :class "quick-settings"
|
||||
:orientation "v"
|
||||
:space-evenly false
|
||||
(label :text "Control Center"
|
||||
:class "title"
|
||||
:xalign 0.04
|
||||
)
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
;; Button Grid
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
(box :class "button-grid"
|
||||
:orientation "v"
|
||||
:valign "start"
|
||||
:width 0
|
||||
:height 0
|
||||
:halign "center"
|
||||
:space-evenly false
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
;; Row ONE
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
(box :class "button-row"
|
||||
:orientation "h"
|
||||
:space-evenly true
|
||||
:width 0
|
||||
:height 0
|
||||
:halign "center"
|
||||
:style "margin-top: 15px;
|
||||
margin-bottom: 7px"
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
(box :class "grid-button"
|
||||
:orientation "h"
|
||||
:space-evenly false
|
||||
:width 0
|
||||
:height 0
|
||||
|
||||
(eventbox :class "left-part"
|
||||
:cursor "pointer"
|
||||
:onclick "$EWW_PATH/network.sh toggle"
|
||||
(label :text " ${network_icon} "
|
||||
:class "grid-label"
|
||||
)
|
||||
)
|
||||
(eventbox :class "right-part"
|
||||
:cursor "pointer"
|
||||
:onclick "nm-connection-editor &"
|
||||
|
||||
(label :text " " :class "grid-chev")
|
||||
)
|
||||
)
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
(box :class "grid-button"
|
||||
:orientation "h"
|
||||
:space-evenly false
|
||||
:width 0
|
||||
:height 0
|
||||
|
||||
(eventbox :class "left-part"
|
||||
:cursor "pointer"
|
||||
:onclick "$EWW_PATH/bluetooth.sh toggle"
|
||||
|
||||
(label :text " ${bluetooth_icon} "
|
||||
:class "grid-label"
|
||||
)
|
||||
)
|
||||
(eventbox :class "right-part"
|
||||
:cursor "pointer"
|
||||
:onclick "blueberry &"
|
||||
|
||||
(label :text " " :class "grid-chev")
|
||||
)
|
||||
)
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
(box :class "grid-button"
|
||||
:orientation "h"
|
||||
:space-evenly false
|
||||
:width 0
|
||||
:height 0
|
||||
|
||||
(eventbox :class "left-part"
|
||||
:cursor "pointer"
|
||||
:onclick "$EWW_PATH/network.sh toggle-radio"
|
||||
|
||||
(label :text "${network_radio == 'on' ? ' ' : ' '}"
|
||||
:class "grid-label"
|
||||
)
|
||||
)
|
||||
(eventbox :class "right-part"
|
||||
:cursor "pointer"
|
||||
:onclick "notify-send 'set this up moron'"
|
||||
|
||||
(label :text " "
|
||||
:class "grid-chev"
|
||||
)
|
||||
)
|
||||
)
|
||||
)
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
;; SUB ROW
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
(box :orientation "h"
|
||||
:space-evenly true
|
||||
:spacing 34
|
||||
:width 0
|
||||
:height 0
|
||||
:halign "center"
|
||||
|
||||
|
||||
(label :text "${network_ssid}"
|
||||
:class "sub-label"
|
||||
:width 0
|
||||
:height 0
|
||||
:xalign 0.4
|
||||
:limit-width 12
|
||||
)
|
||||
|
||||
(label :text "${bluetooth_dev}"
|
||||
:class "sub-label"
|
||||
:width 0
|
||||
:height 0
|
||||
:xalign 0.4
|
||||
:limit-width 12
|
||||
)
|
||||
|
||||
(label :text ""
|
||||
:class ""
|
||||
:width 0
|
||||
:height 0
|
||||
:xalign 0.4
|
||||
:limit-width 12
|
||||
)
|
||||
)
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
;; Row TWO
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
(box :class "button-row"
|
||||
:orientation "h"
|
||||
:space-evenly true
|
||||
:width 0
|
||||
:height 0
|
||||
:halign "center"
|
||||
:style "margin-top: 7px;
|
||||
margin-bottom: 15px;"
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
(box :class "grid-button"
|
||||
:orientation "h"
|
||||
:space-evenly false
|
||||
:width 0
|
||||
:height 0
|
||||
|
||||
(eventbox :class "left-part"
|
||||
:cursor "pointer"
|
||||
:onclick "swayosd --output-volume mute-toggle"
|
||||
|
||||
(label :text " ${volume_icon} "
|
||||
:class "grid-label"
|
||||
)
|
||||
)
|
||||
(eventbox :class "right-part"
|
||||
:cursor "pointer"
|
||||
:onclick "pavucontrol &"
|
||||
|
||||
(label :text " " :class "grid-chev")
|
||||
)
|
||||
)
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
(box :class "grid-button"
|
||||
:orientation "h"
|
||||
:space-evenly false
|
||||
:width 0
|
||||
:height 0
|
||||
|
||||
(eventbox :class "left-part"
|
||||
:cursor "pointer"
|
||||
:onclick "$EWW_PATH/mic.sh toggle-muted"
|
||||
|
||||
(label :text " ${mic_icon} "
|
||||
:class "grid-label"
|
||||
)
|
||||
)
|
||||
(eventbox :class "right-part"
|
||||
:cursor "pointer"
|
||||
:onclick "pavucontrol &"
|
||||
|
||||
(label :text " " :class "grid-chev")
|
||||
)
|
||||
)
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
(box :class "grid-button"
|
||||
:orientation "h"
|
||||
:space-evenly false
|
||||
:width 0
|
||||
:height 0
|
||||
|
||||
(eventbox :class "left-part"
|
||||
:cursor "pointer"
|
||||
:onclick "$LOCK_PATH/lock.sh &"
|
||||
|
||||
(label :text " "
|
||||
:class "grid-label"
|
||||
)
|
||||
)
|
||||
(eventbox :class "right-part"
|
||||
:cursor "pointer"
|
||||
:onclick "$EWW_PATH/open.sh powermenu"
|
||||
|
||||
(label :text " " :class "grid-chev")
|
||||
)
|
||||
)
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
)
|
||||
)
|
||||
(box :class "slider-box"
|
||||
:orientation "v"
|
||||
:space-evenly true
|
||||
:spacing 0
|
||||
:width 0
|
||||
:height 0
|
||||
:halign "center"
|
||||
|
||||
(box :class "slider"
|
||||
:orientation "h"
|
||||
:valign "start"
|
||||
:halign "center"
|
||||
:width 0
|
||||
:height 0
|
||||
:space-evenly false
|
||||
|
||||
(label :text "${volume_icon}" :class "slider-label")
|
||||
|
||||
(scale :value volume_value
|
||||
:onchange "$EWW_PATH/volume.sh set {}"
|
||||
:min 0
|
||||
:max 101
|
||||
:height 0
|
||||
:width 0
|
||||
)
|
||||
)
|
||||
(box :class "slider"
|
||||
:orientation "h"
|
||||
:valign "start"
|
||||
:halign "center"
|
||||
:width 0
|
||||
:height 0
|
||||
:space-evenly false
|
||||
|
||||
(label :text " ${br_icon} " :class "slider-label" :style "margin-left: 6px;
|
||||
margin-right: -6px")
|
||||
|
||||
(scale :value br
|
||||
:onchange "$EWW_PATH/brightness.sh set {}"
|
||||
:min 0
|
||||
:max 256
|
||||
:height 0
|
||||
:width 0
|
||||
)
|
||||
)
|
||||
)
|
||||
(centerbox :orientation "h"
|
||||
:style "margin-bottom: 10px;"
|
||||
(label)
|
||||
|
||||
(revealer :reveal showplayer
|
||||
(eventbox :cursor "pointer"
|
||||
:onclick "${expand_player == 'true' ? 'eww update expand_player=false' : 'eww update expand_player=true'}"
|
||||
"${expand_player == 'true' ? ' ' : ' ' }"
|
||||
)
|
||||
)
|
||||
|
||||
(label)
|
||||
)
|
||||
)
|
||||
(revealer :reveal expand_player
|
||||
:transition "slidedown"
|
||||
(box :class "player"
|
||||
:style "${expand_player == 'true' ? 'opacity: 1; transition: opacity ${anim_duration}' :
|
||||
'opacity: 0; transition: opacity ${anim_duration}'}"
|
||||
(playerinfo)
|
||||
)
|
||||
)
|
||||
)
|
||||
)
|
||||
(defwindow quick-settings-reveal
|
||||
:monitor 0
|
||||
:stacking "overlay"
|
||||
:geometry (geometry :x "5px"
|
||||
:y "7px"
|
||||
:width "0px"
|
||||
:height "0px"
|
||||
:anchor "top right"
|
||||
)
|
||||
(revealer
|
||||
:transition "crossfade"
|
||||
:reveal showqs
|
||||
:duration anim_duration
|
||||
(quick-settings)
|
||||
)
|
||||
)
|
35
config/eww/scripts/bluetooth.sh
Executable file
35
config/eww/scripts/bluetooth.sh
Executable file
|
@ -0,0 +1,35 @@
|
|||
#!/usr/bin/env bash
|
||||
|
||||
FILE="$HOME/.config/.bluetooth"
|
||||
|
||||
get_device() {
|
||||
if [[ $(bluetoothctl devices Connected) != "" ]]; then
|
||||
bluetoothctl devices Connected | awk '{ for (i = 3; i <= NF; i++) { printf("%s ", $i) } printf("\n") }'
|
||||
else
|
||||
echo "Disconnected"
|
||||
fi
|
||||
}
|
||||
|
||||
get_state() {
|
||||
if [[ "$(rfkill list | grep -A 1 hci0 | grep -o no)" == "no" ]]; then
|
||||
eww update bluetooth_icon=" "
|
||||
echo " " > "$FILE"
|
||||
else
|
||||
eww update bluetooth_icon=" "
|
||||
echo " " > "$FILE"
|
||||
fi
|
||||
}
|
||||
|
||||
[[ "$1" == "device" ]] && get_device
|
||||
if [[ "$1" == "toggle" ]]; then
|
||||
rfkill toggle bluetooth
|
||||
get_state
|
||||
fi
|
||||
|
||||
if [[ $1 == "icon" ]]; then
|
||||
while true; do
|
||||
get_state
|
||||
tail "$FILE"
|
||||
sleep 1
|
||||
done
|
||||
fi
|
46
config/eww/scripts/brightness.sh
Executable file
46
config/eww/scripts/brightness.sh
Executable file
|
@ -0,0 +1,46 @@
|
|||
#!/usr/bin/env bash
|
||||
|
||||
get_icon () {
|
||||
val=$(brightnessctl get)
|
||||
|
||||
if [ "$val" -le 3 ]; then
|
||||
eww update br_icon=" "
|
||||
|
||||
elif [ "$val" -le 38 ]; then
|
||||
eww update br_icon=" "
|
||||
|
||||
elif [ "$val" -le 77 ]; then
|
||||
eww update br_icon=" "
|
||||
|
||||
elif [ "$val" -le 115 ]; then
|
||||
eww update br_icon=" "
|
||||
|
||||
elif [ "$val" -le 153 ]; then
|
||||
eww update br_icon=" "
|
||||
|
||||
elif [ "$val" -le 191 ]; then
|
||||
eww update br_icon=" "
|
||||
|
||||
elif [ "$val" -le 230 ]; then
|
||||
eww update br_icon=" "
|
||||
|
||||
else
|
||||
eww update br_icon=" "
|
||||
fi
|
||||
}
|
||||
|
||||
if [[ $1 == "br" ]]; then
|
||||
brightnessctl get
|
||||
fi
|
||||
|
||||
if [[ $1 == "icon" ]]; then
|
||||
while true; do
|
||||
get_icon
|
||||
sleep 1
|
||||
done
|
||||
fi
|
||||
|
||||
if [[ $1 == "set" ]]; then
|
||||
brightnessctl set "$2"
|
||||
get_icon
|
||||
fi
|
20
config/eww/scripts/close-opened.sh
Executable file
20
config/eww/scripts/close-opened.sh
Executable file
|
@ -0,0 +1,20 @@
|
|||
#!/usr/bin/env bash
|
||||
|
||||
# Store the output of the command in an array, keeping only lines with '*'
|
||||
readarray -t array <<< "$(eww windows | grep '^\*')"
|
||||
|
||||
# Remove the '*' from each element
|
||||
for ((i=0; i<${#array[@]}; i++))
|
||||
do
|
||||
array[i]=${array[i]#'*'}
|
||||
done
|
||||
|
||||
# Close every window except permanent ones
|
||||
for element in "${array[@]}"
|
||||
do
|
||||
[[ "$element" != "left-bar" ]] &&
|
||||
[[ "$element" != "notif-panel" ]] &&
|
||||
[[ "$element" != "quick-settings-toggle" ]] &&
|
||||
[[ "$element" != "playerinfo" ]] &&
|
||||
eww close "$element"
|
||||
done
|
46
config/eww/scripts/heart.sh
Executable file
46
config/eww/scripts/heart.sh
Executable file
|
@ -0,0 +1,46 @@
|
|||
#!/usr/bin/env bash
|
||||
|
||||
FILE="$HOME/.config/.heart"
|
||||
|
||||
toggle() {
|
||||
if grep -q "$FILE"; then
|
||||
eww update heart-ts=false
|
||||
echo > "$FILE"
|
||||
else
|
||||
eww update heart-ts=true
|
||||
echo >> "$FILE"
|
||||
fi
|
||||
}
|
||||
|
||||
[[ "$1" == "toggle" ]] && toggle
|
||||
|
||||
|
||||
startup() {
|
||||
(
|
||||
if [[ ! -f "$FILE" ]]; then
|
||||
echo > "$FILE"
|
||||
fi
|
||||
|
||||
if [[ ! -f "$HOME/.config/.bluetooth" ]]; then
|
||||
echo > "$FILE"
|
||||
fi
|
||||
|
||||
if grep -q "$HOME/.config/.bluetooth"; then
|
||||
rfkill block bluetooth
|
||||
fi
|
||||
|
||||
"$HYPR_PATH"/osk-toggle.sh getState &
|
||||
"$EWW_PATH"/on-release.sh &
|
||||
"$EWW_PATH"/music.sh accents &
|
||||
input-emulator start mouse -n &
|
||||
|
||||
if grep -q "$FILE"; then
|
||||
sleep 0.9 &&
|
||||
eww update heart-ts=true
|
||||
fi
|
||||
) &
|
||||
|
||||
tail -f "$FILE"
|
||||
}
|
||||
|
||||
[[ "$1" == "startup" ]] && startup
|
30
config/eww/scripts/mic.sh
Executable file
30
config/eww/scripts/mic.sh
Executable file
|
@ -0,0 +1,30 @@
|
|||
#!/usr/bin/env bash
|
||||
|
||||
SOURCE="@DEFAULT_SOURCE@"
|
||||
|
||||
is_muted () {
|
||||
pactl get-source-mute $SOURCE | awk '{print $2}'
|
||||
}
|
||||
|
||||
get_icon () {
|
||||
if [[ $(is_muted) == "yes" ]]; then
|
||||
echo " "
|
||||
else
|
||||
echo " "
|
||||
fi
|
||||
}
|
||||
|
||||
if [[ $1 == "icon" ]]; then
|
||||
while true; do
|
||||
sleep 0.01
|
||||
get_icon
|
||||
done
|
||||
fi
|
||||
|
||||
if [[ $1 == "muted" ]]; then
|
||||
is_muted
|
||||
fi
|
||||
|
||||
if [[ $1 == "toggle-muted" ]]; then
|
||||
swayosd --input-volume mute-toggle
|
||||
fi
|
87
config/eww/scripts/music.sh
Executable file
87
config/eww/scripts/music.sh
Executable file
|
@ -0,0 +1,87 @@
|
|||
#!/usr/bin/env bash
|
||||
|
||||
loop() {
|
||||
loop_status=$(playerctl -p Spot loop)
|
||||
|
||||
case $loop_status in
|
||||
"None" )
|
||||
playerctl -p Spot loop Playlist
|
||||
eww update repeat_icon=""
|
||||
;;
|
||||
"Track" )
|
||||
playerctl -p Spot loop None
|
||||
eww update repeat_icon=""
|
||||
;;
|
||||
"Playlist" )
|
||||
playerctl -p Spot loop Track
|
||||
eww update repeat_icon=""
|
||||
;;
|
||||
* )
|
||||
echo "Unknown loop status."
|
||||
;;
|
||||
esac
|
||||
}
|
||||
|
||||
loop_status() {
|
||||
loop_status=$(playerctl -p Spot loop)
|
||||
|
||||
case $loop_status in
|
||||
"None" )
|
||||
eww update repeat_icon=""
|
||||
;;
|
||||
"Track" )
|
||||
eww update repeat_icon=""
|
||||
;;
|
||||
"Playlist" )
|
||||
eww update repeat_icon=""
|
||||
;;
|
||||
* )
|
||||
echo "Unknown loop status."
|
||||
;;
|
||||
esac
|
||||
}
|
||||
|
||||
get_length() {
|
||||
if [[ $(eww get get_pos) == "true" ]]; then
|
||||
eww update song_pos="$(playerctl -p Spot position)"
|
||||
fi
|
||||
eww update song_length="$(echo "$(playerctl -p Spot metadata mpris:length)/1000000" | bc -l)"
|
||||
}
|
||||
|
||||
get_accents() {
|
||||
accents="$(coloryou /tmp/cover.jpg | sed 's/,//g' | sed 's/}//' | sed 's/'\''//g')"
|
||||
music_accent=$(echo "$accents" | awk '{ print $2 }')
|
||||
eww update music_accent="$music_accent"
|
||||
|
||||
button_accent=$(echo "$accents" | awk '{ print $4 }')
|
||||
eww update button_accent="$button_accent"
|
||||
|
||||
button_text=$(echo "$accents" | awk '{ print $6 }')
|
||||
eww update button_text="$button_text"
|
||||
}
|
||||
|
||||
get_cover() {
|
||||
existing_file="/tmp/cover.jpg"
|
||||
new_image_url=$(playerctl -p Spot metadata mpris:artUrl)
|
||||
existing_hash=$(md5sum "$existing_file" | awk '{print $1}')
|
||||
|
||||
# Download the new image only if the hashes are different
|
||||
if [[ "$(wget -qO- "$new_image_url" | md5sum | awk '{print $1}')" != "$existing_hash" ]]; then
|
||||
wget -qO "$existing_file" "$new_image_url"
|
||||
get_accents
|
||||
fi
|
||||
|
||||
if [[ -s "/tmp/cover.jpg" ]]; then
|
||||
eww update showplayer=true
|
||||
echo "/tmp/cover.jpg"
|
||||
else
|
||||
eww update showplayer=false
|
||||
echo "randomfile"
|
||||
fi
|
||||
}
|
||||
|
||||
[[ "$1" == "accents" ]] && get_accents
|
||||
[[ "$1" == "loop" ]] && loop
|
||||
[[ "$1" == "loop_status" ]] && loop_status
|
||||
[[ "$1" == "length" ]] && get_length
|
||||
[[ "$1" == "cover" ]] && get_cover
|
53
config/eww/scripts/network.sh
Executable file
53
config/eww/scripts/network.sh
Executable file
|
@ -0,0 +1,53 @@
|
|||
#!/usr/bin/env bash
|
||||
|
||||
get_ssid() {
|
||||
if nmcli -t -f NAME c show --active | grep -v lo; then
|
||||
true
|
||||
else
|
||||
echo "Disconnected"
|
||||
fi
|
||||
}
|
||||
|
||||
get_state() {
|
||||
if [[ "$(rfkill list | grep -A 1 LAN | grep -o no)" == "no" ]]; then
|
||||
eww update network_icon=" "
|
||||
else
|
||||
eww update network_icon=" "
|
||||
fi
|
||||
}
|
||||
|
||||
[[ "$1" == "ssid" ]] && get_ssid
|
||||
|
||||
if [[ "$1" == "toggle" ]]; then
|
||||
rfkill toggle wlan
|
||||
get_state
|
||||
fi
|
||||
|
||||
if [[ $1 == "icon" ]]; then
|
||||
while true; do
|
||||
get_state
|
||||
sleep 1
|
||||
done
|
||||
fi
|
||||
|
||||
radio_status () {
|
||||
radio_status=$(nmcli radio wifi)
|
||||
if [[ $radio_status == "enabled" ]]; then
|
||||
echo "on"
|
||||
else
|
||||
echo "off"
|
||||
fi
|
||||
}
|
||||
|
||||
if [[ $1 == "radio-status" ]]; then
|
||||
radio_status
|
||||
fi
|
||||
|
||||
if [[ $1 == "toggle-radio" ]]; then
|
||||
stat=$(radio_status)
|
||||
if [[ $stat == "on" ]]; then
|
||||
nmcli radio wifi off
|
||||
else
|
||||
nmcli radio wifi on
|
||||
fi
|
||||
fi
|
29
config/eww/scripts/notif-toggle.sh
Executable file
29
config/eww/scripts/notif-toggle.sh
Executable file
|
@ -0,0 +1,29 @@
|
|||
#!/usr/bin/env bash
|
||||
|
||||
on() {
|
||||
# open notif panel
|
||||
swaync-client -op
|
||||
|
||||
# open closers to close when outside control center
|
||||
eww open closer-notif1
|
||||
eww open closer-notif2
|
||||
eww open closer-notif3
|
||||
eww open closer-notif4
|
||||
|
||||
eww close notif-panel; eww open notif-panel &&
|
||||
eww update notif-panel-state=true
|
||||
}
|
||||
|
||||
off() {
|
||||
swaync-client -cp
|
||||
|
||||
eww update notif-panel-state=false
|
||||
|
||||
eww close closer-notif1
|
||||
eww close closer-notif2
|
||||
eww close closer-notif3
|
||||
eww close closer-notif4
|
||||
}
|
||||
|
||||
[[ "$1" == "on" ]] && on
|
||||
[[ "$1" == "off" ]] && off
|
30
config/eww/scripts/notif.sh
Executable file
30
config/eww/scripts/notif.sh
Executable file
|
@ -0,0 +1,30 @@
|
|||
#!/usr/bin/env bash
|
||||
|
||||
state () {
|
||||
if [[ $(hyprctl layers | grep swaync-control-center) == "" ]]; then
|
||||
if [[ $(eww get notif-panel-state) == "true" ]]; then
|
||||
eww update notif-panel-state=false
|
||||
fi
|
||||
fi
|
||||
}
|
||||
|
||||
icon () {
|
||||
COUNT=$(swaync-client -c)
|
||||
|
||||
if [[ $(swaync-client -D) == "true" ]]; then
|
||||
echo " "
|
||||
elif [[ $COUNT == "0" ]]; then
|
||||
echo "$COUNT "
|
||||
else
|
||||
echo "$COUNT "
|
||||
fi
|
||||
state
|
||||
}
|
||||
|
||||
if [[ $1 == "icon" ]]; then
|
||||
while true; do
|
||||
sleep 0.01
|
||||
icon
|
||||
done
|
||||
fi
|
||||
|
22
config/eww/scripts/on-release.sh
Executable file
22
config/eww/scripts/on-release.sh
Executable file
|
@ -0,0 +1,22 @@
|
|||
#!/usr/bin/env bash
|
||||
|
||||
FILE="$HOME/.config/.on-release"
|
||||
|
||||
function run() {
|
||||
echo "can_run" > "$FILE"
|
||||
}
|
||||
|
||||
while IFS='$\n' read -r line; do
|
||||
if [[ $(echo "$line" | grep TOUCH_UP) != "" ]]; then
|
||||
run
|
||||
if [[ $(echo "$line" | grep '1 (1)') != "" ]]; then
|
||||
eww update cancel_touch=false
|
||||
fi
|
||||
elif [[ $(echo "$line" | grep release) != "" ]]; then
|
||||
run
|
||||
elif [[ $(echo "$line" | grep 'TOUCH_DOWN.*1 (1)') != "" ]]; then
|
||||
eww update cancel_touch=true
|
||||
else
|
||||
echo "other" > "$FILE"
|
||||
fi
|
||||
done < <(stdbuf -oL libinput debug-events)
|
7
config/eww/scripts/open.sh
Executable file
7
config/eww/scripts/open.sh
Executable file
|
@ -0,0 +1,7 @@
|
|||
#!/usr/bin/env bash
|
||||
eww open closer &&
|
||||
|
||||
WINDOW="$1"
|
||||
|
||||
eww open "$WINDOW"-reveal
|
||||
eww update "$WINDOW"-visible=true
|
20
config/eww/scripts/qs-toggle.sh
Executable file
20
config/eww/scripts/qs-toggle.sh
Executable file
|
@ -0,0 +1,20 @@
|
|||
#!/usr/bin/env bash
|
||||
|
||||
on () {
|
||||
eww open closer &&
|
||||
|
||||
eww open quick-settings-reveal;
|
||||
eww open quick-settings-smol-reveal;
|
||||
eww open quick-settings-logo-reveal;
|
||||
eww update showqs=true
|
||||
}
|
||||
|
||||
off () {
|
||||
eww update showqs=false
|
||||
eww close quick-settings-reveal
|
||||
eww close quick-settings-smol-reveal
|
||||
eww close quick-settings-logo-reveal
|
||||
}
|
||||
|
||||
[[ "$1" == "on" ]] && on
|
||||
[[ "$1" == "off" ]] && off
|
22
config/eww/scripts/run.sh
Executable file
22
config/eww/scripts/run.sh
Executable file
|
@ -0,0 +1,22 @@
|
|||
#!/usr/bin/env bash
|
||||
|
||||
FILE="$HOME/.config/.on-release"
|
||||
SCRIPT="$1"
|
||||
VAR="$2"
|
||||
|
||||
function run() {
|
||||
if [[ $(eww get "$VAR") == "true" ]]; then
|
||||
if [[ $(eww get cancel_touch) == "false" ]]; then
|
||||
bash -c "$SCRIPT"
|
||||
fi
|
||||
else
|
||||
eww open on-release-fix
|
||||
sleep 0.1
|
||||
input-emulator mouse button left
|
||||
fi
|
||||
exit 0
|
||||
}
|
||||
|
||||
while IFS='$\n' read -r line; do
|
||||
[[ $(grep "can_run" "$FILE") != "" ]] && run
|
||||
done < <(stdbuf -oL tail -f "$FILE")
|
90
config/eww/scripts/volume.sh
Executable file
90
config/eww/scripts/volume.sh
Executable file
|
@ -0,0 +1,90 @@
|
|||
#!/usr/bin/env bash
|
||||
|
||||
SINK="@DEFAULT_SINK@"
|
||||
|
||||
percentage () {
|
||||
local val=$(echo $1 | tr '%' ' ' | awk '{print $1}')
|
||||
local icon1=$2
|
||||
local icon2=$3
|
||||
local icon3=$4
|
||||
local icon4=$5
|
||||
if [ "$val" -le 15 ]; then
|
||||
echo $icon1
|
||||
elif [ "$val" -le 30 ]; then
|
||||
echo $icon2
|
||||
elif [ "$val" -le 60 ]; then
|
||||
echo $icon3
|
||||
else
|
||||
echo $icon4
|
||||
fi
|
||||
}
|
||||
|
||||
is_muted () {
|
||||
pactl get-sink-mute $SINK | awk '{print $2}'
|
||||
}
|
||||
|
||||
get_percentage () {
|
||||
if [[ $(is_muted) == 'yes' ]]; then
|
||||
echo 0%
|
||||
else
|
||||
vol=$(pactl get-sink-volume @DEFAULT_SINK@ | grep Volume | awk '{print $5}' | tr % " ")
|
||||
echo "${vol}%"
|
||||
fi
|
||||
}
|
||||
|
||||
get_icon () {
|
||||
local vol=$(get_percentage)
|
||||
if [[ $vol == "0%" ]]; then
|
||||
echo " 婢"
|
||||
else
|
||||
echo $(percentage "$vol" "" "" "墳" "")
|
||||
fi
|
||||
}
|
||||
|
||||
get_class () {
|
||||
local vol=$(get_percentage)
|
||||
if [[ $vol == "0%" ]]; then
|
||||
echo "red"
|
||||
else
|
||||
echo $(percentage "$vol" "red" "magenta" "yellow" "blue")
|
||||
fi
|
||||
}
|
||||
|
||||
get_vol () {
|
||||
echo $(pactl get-sink-volume @DEFAULT_SINK@ | grep Volume | awk '{print $5}' | tr % " ")
|
||||
}
|
||||
|
||||
if [[ $1 == "icon" ]]; then
|
||||
while true; do
|
||||
sleep 0.01
|
||||
get_icon
|
||||
done
|
||||
fi
|
||||
|
||||
if [[ $1 == "class" ]]; then
|
||||
get_class
|
||||
fi
|
||||
|
||||
if [[ $1 == "percentage" ]]; then
|
||||
get_percentage
|
||||
fi
|
||||
|
||||
if [[ $1 == "vol" ]]; then
|
||||
get_vol
|
||||
fi
|
||||
|
||||
if [[ $1 == "muted" ]]; then
|
||||
is_muted
|
||||
fi
|
||||
|
||||
if [[ $1 == "toggle-muted" ]]; then
|
||||
pactl set-sink-mute $SINK toggle
|
||||
fi
|
||||
|
||||
if [[ $1 == "set" ]]; then
|
||||
val=$(echo $2 | tr '.' ' ' | awk '{print $1}')
|
||||
if test $val -gt 100; then
|
||||
val=100
|
||||
fi
|
||||
pactl set-sink-volume $SINK $val%
|
||||
fi
|
76
config/eww/traybuttons/traybuttons.scss
Normal file
76
config/eww/traybuttons/traybuttons.scss
Normal file
|
@ -0,0 +1,76 @@
|
|||
.osk-toggle {
|
||||
font-size: 28px;
|
||||
min-height: 40px;
|
||||
min-width: 50px;
|
||||
padding: 0px 0px 0px 5px;
|
||||
}
|
||||
|
||||
.tablet-toggle {
|
||||
font-size: 28px;
|
||||
min-height: 40px;
|
||||
min-width: 50px;
|
||||
padding: 0px 0px 0px 5px;
|
||||
}
|
||||
|
||||
.heart-toggle {
|
||||
font-size: 28px;
|
||||
min-height: 40px;
|
||||
min-width: 50px;
|
||||
padding: 0px 0px 0px 4px;
|
||||
}
|
||||
|
||||
.notif-panel {
|
||||
font-size: 20px;
|
||||
border-radius: 80px;
|
||||
min-height: 37px;
|
||||
min-width: 105px;
|
||||
padding: 1px 0px 1px 5px;
|
||||
|
||||
.toggle-on {
|
||||
border-top-left-radius: 22px;
|
||||
border-top-right-radius: 22px;
|
||||
border-bottom-left-radius: 0px;
|
||||
border-bottom-right-radius: 0px;
|
||||
border-bottom: 0px solid $bg;
|
||||
}
|
||||
}
|
||||
|
||||
.filler {
|
||||
border-left: 2px solid $contrastbg;
|
||||
border-right: 2px solid $contrastbg;
|
||||
min-height: 14px;
|
||||
min-width: 105px;
|
||||
background-color: $bg;
|
||||
transition: all 0.5s;
|
||||
}
|
||||
|
||||
.quick-settings-toggle {
|
||||
font-size: 24px;
|
||||
min-height: 40px;
|
||||
min-width: 40px;
|
||||
padding: 0px 0px 0px 0px;
|
||||
}
|
||||
|
||||
.toggle-off {
|
||||
background-color: $bg;
|
||||
color: #CBA6F7;
|
||||
border-radius: 80px;
|
||||
border: 2px solid #1b1b2b;
|
||||
transition: background-color 0.5s ease-in-out,
|
||||
border 0.5s ease-in-out;
|
||||
}
|
||||
|
||||
.toggle-on {
|
||||
background-color: $bg;
|
||||
color: #CBA6F7;
|
||||
border-radius: 80px;
|
||||
border: 2px solid $contrastbg;
|
||||
transition: background-color 0.5s ease-in-out,
|
||||
border 0.5s ease-in-out;
|
||||
}
|
||||
|
||||
.toggle-on:hover, .toggle-off:hover {
|
||||
background-color: rgba(127, 132, 156, 0.4);
|
||||
transition: background-color 0.5s ease-in-out,
|
||||
border 0.5s ease-in-out;
|
||||
}
|
164
config/eww/traybuttons/traybuttons.yuck
Normal file
164
config/eww/traybuttons/traybuttons.yuck
Normal file
|
@ -0,0 +1,164 @@
|
|||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
;; On-Screen Keyboard Toggle
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
(defvar osk-ts false)
|
||||
(defvar osk-run "false")
|
||||
|
||||
(defwidget osk-toggle []
|
||||
(eventbox :class "${osk-ts == 'true' ? 'toggle-on' : 'toggle-off'}"
|
||||
:onclick "$EWW_PATH/run.sh '$HYPR_PATH/osk-toggle.sh toggle' osk-run &"
|
||||
:cursor "pointer"
|
||||
:onhover "eww update osk-run=true"
|
||||
:onhoverlost "eww update osk-run=false"
|
||||
|
||||
(box :class "osk-toggle"
|
||||
:orientation "h"
|
||||
(label :text " ")
|
||||
)
|
||||
)
|
||||
)
|
||||
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
;; Tablet Mode Toggle
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
(defvar tablet-ts false)
|
||||
(defvar tablet-run "false")
|
||||
|
||||
(defvar turn-tablet-off "$EWW_PATH/run.sh '$HYPR_PATH/laptop-mode.sh' tablet-run &")
|
||||
(defvar turn-tablet-on "$EWW_PATH/run.sh '$HYPR_PATH/tablet-mode.sh' tablet-run &")
|
||||
|
||||
(defwidget tablet-toggle []
|
||||
(eventbox :class "${tablet-ts == 'true' ? 'toggle-on' : 'toggle-off'}"
|
||||
:onclick "${tablet-ts == 'true' ? turn-tablet-off : turn-tablet-on}"
|
||||
:cursor "pointer"
|
||||
:onhover "eww update tablet-run=true"
|
||||
:onhoverlost "eww update tablet-run=false"
|
||||
|
||||
(box :class "tablet-toggle"
|
||||
:orientation "h"
|
||||
(label :text " ")
|
||||
)
|
||||
)
|
||||
)
|
||||
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
;; Heart Toggle
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
(defvar heart-ts "false")
|
||||
(defvar heart-run "false")
|
||||
|
||||
(defwidget heart-toggle []
|
||||
(eventbox :class "${heart-ts == 'true' ? 'toggle-on' : 'toggle-off'}"
|
||||
:onclick "$EWW_PATH/run.sh '$EWW_PATH/heart.sh toggle' heart-run &"
|
||||
:cursor "pointer"
|
||||
:onhover "eww update heart-run=true"
|
||||
:onhoverlost "eww update heart-run=false"
|
||||
|
||||
(box :class "heart-toggle"
|
||||
:orientation "h"
|
||||
(label :text " ${heart_icon} ")
|
||||
)
|
||||
)
|
||||
)
|
||||
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
;; Left Bar
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
(defwidget left-bar []
|
||||
(box :class "transparent"
|
||||
:space-evenly true
|
||||
:spacing 12
|
||||
:orientation "h"
|
||||
(osk-toggle)
|
||||
(tablet-toggle)
|
||||
(heart-toggle)
|
||||
)
|
||||
)
|
||||
(defwindow left-bar
|
||||
:monitor 0
|
||||
:stacking "overlay"
|
||||
:exclusive "ignore"
|
||||
:geometry (geometry :x "5px"
|
||||
:y "10px"
|
||||
:width "0px"
|
||||
:height "0px"
|
||||
:anchor "top left"
|
||||
)
|
||||
(left-bar)
|
||||
)
|
||||
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
;; Quick Settings Toggle
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
(defvar qs-run-on "false")
|
||||
(defwidget quick-settings-toggle []
|
||||
(eventbox :class "toggle-off"
|
||||
:onclick "$EWW_PATH/run.sh '$EWW_PATH/qs-toggle.sh on' qs-run-on &"
|
||||
:cursor "pointer"
|
||||
:onhover "eww update qs-run-on=true"
|
||||
:onhoverlost "eww update qs-run-on=false"
|
||||
|
||||
(box :class "quick-settings-toggle"
|
||||
:orientation "h"
|
||||
(label :text " ")
|
||||
)
|
||||
)
|
||||
)
|
||||
(defwindow quick-settings-toggle
|
||||
:monitor 0
|
||||
:stacking "overlay"
|
||||
:exclusive "ignore"
|
||||
:geometry (geometry :x "5px"
|
||||
:y "10px"
|
||||
:width "0px"
|
||||
:height "0px"
|
||||
:anchor "top right"
|
||||
)
|
||||
(quick-settings-toggle)
|
||||
)
|
||||
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
;; Notification Panel Toggle
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
(defvar notif-panel-state false)
|
||||
(defvar notif-run "false")
|
||||
(defvar turn-notif-on "$EWW_PATH/run.sh '$EWW_PATH/notif-toggle.sh on' notif-run &")
|
||||
(defvar turn-notif-off "$EWW_PATH/run.sh '$EWW_PATH/notif-toggle.sh off' notif-run &")
|
||||
|
||||
(defwidget notif-panel []
|
||||
(box :orientation "v"
|
||||
:space-evenly false
|
||||
:spacing 0
|
||||
(eventbox :class "${notif-panel-state == 'true' ? 'toggle-on' : 'toggle-off'}"
|
||||
:onclick "${notif-panel-state == 'true' ? turn-notif-off : turn-notif-on}"
|
||||
:cursor "pointer"
|
||||
:onhover "eww update notif-run=true"
|
||||
:onhoverlost "eww update notif-run=false"
|
||||
|
||||
(box :class "notif-panel"
|
||||
:orientation "v"
|
||||
(label :text " ${notif_icon} ")
|
||||
)
|
||||
)
|
||||
(revealer :reveal notif-panel-state
|
||||
:duration anim_duration
|
||||
:transition "slideup"
|
||||
:height 0
|
||||
(box :class "filler"
|
||||
:height 0
|
||||
)
|
||||
)
|
||||
)
|
||||
)
|
||||
(defwindow notif-panel
|
||||
:monitor 0
|
||||
:stacking "overlay"
|
||||
:exclusive "ignore"
|
||||
:geometry (geometry :x "60px"
|
||||
:y "10px"
|
||||
:width "0px"
|
||||
:height "0px"
|
||||
:anchor "top right"
|
||||
)
|
||||
(notif-panel)
|
||||
)
|
33
config/eww/variables.yuck
Normal file
33
config/eww/variables.yuck
Normal file
|
@ -0,0 +1,33 @@
|
|||
; this var starts all scripts needed when eww boots
|
||||
(deflisten heart_icon "$EWW_PATH/heart.sh startup")
|
||||
(defvar cancel_touch "false")
|
||||
|
||||
(deflisten notif_icon "$EWW_PATH/notif.sh icon")
|
||||
(deflisten mic_icon "$EWW_PATH/mic.sh icon")
|
||||
|
||||
(deflisten network_ssid "zscroll -d 0.7 -l 12 -p '. ' -u true \"$EWW_PATH/network.sh ssid\"")
|
||||
(deflisten network_icon "$EWW_PATH/network.sh icon")
|
||||
(defpoll network_radio :interval "1s" "$EWW_PATH/network.sh radio-status")
|
||||
|
||||
(deflisten bluetooth_dev "zscroll -d 0.7 -l 12 -p '. ' -u true \"$EWW_PATH/bluetooth.sh device\"")
|
||||
(deflisten bluetooth_icon "$EWW_PATH/bluetooth.sh icon")
|
||||
|
||||
(deflisten volume_icon "$EWW_PATH/volume.sh icon")
|
||||
(defpoll volume :interval "1s" "$EWW_PATH/volume.sh percentage")
|
||||
(defpoll volume_value :interval "1s" "$EWW_PATH/volume.sh vol")
|
||||
(defpoll is_muted :interval "1s" "$EWW_PATH/volume.sh muted")
|
||||
|
||||
(deflisten br_icon "$EWW_PATH/brightness.sh icon")
|
||||
(defpoll br :interval "1s" "$EWW_PATH/brightness.sh br")
|
||||
|
||||
(defvar anim_duration "200ms")
|
||||
|
||||
(defpoll completeday :interval "1h" "date '+%A, %d %B'")
|
||||
(defpoll lithour :interval "30m" "date +%H")
|
||||
(defpoll litmin :interval "30s" "date +%M")
|
||||
(defpoll calendar_day :interval "10h" "date '+%d'")
|
||||
(defpoll calendar_month :interval "10h" "date '+%m")
|
||||
(defpoll calendar_year :interval "10h" "date '+%Y'")
|
||||
(defpoll date :interval "30s" "date '+%d %b, %I:%M %p'")
|
||||
(defpoll shortday :interval "1h" "date '+%d %b %y'")
|
||||
(defpoll weekday :interval "24h" "date +%A")
|
4
config/gtklock/config.ini
Normal file
4
config/gtklock/config.ini
Normal file
|
@ -0,0 +1,4 @@
|
|||
[main]
|
||||
modules=/nix/var/nix/profiles/system/sw/lib/gtklock/powerbar-module.so;/nix/var/nix/profiles/system/sw/lib/gtklock/playerctl-module.so
|
||||
|
||||
#;/nix/var/nix/profiles/system/sw/lib/gtklock/userinfo-module.so
|
5
config/gtklock/scripts/blur.sh
Executable file
5
config/gtklock/scripts/blur.sh
Executable file
|
@ -0,0 +1,5 @@
|
|||
#!/usr/bin/env bash
|
||||
|
||||
grim -t jpeg /tmp/image.jpeg
|
||||
convert /tmp/image.jpeg -blur 0x8 /tmp/image.jpeg
|
||||
|
4
config/gtklock/scripts/lock.sh
Executable file
4
config/gtklock/scripts/lock.sh
Executable file
|
@ -0,0 +1,4 @@
|
|||
#!/usr/bin/env bash
|
||||
$HYPR_PATH/laptop-mode.sh &
|
||||
$LOCK_PATH/blur.sh
|
||||
gtklock
|
17
config/gtklock/style.css
Normal file
17
config/gtklock/style.css
Normal file
|
@ -0,0 +1,17 @@
|
|||
@define-color accent rgba(189, 147, 249, 0.8);
|
||||
@define-color background rgb(40, 42, 54);
|
||||
|
||||
window {
|
||||
background-image: url("/tmp/image.jpeg");
|
||||
background-size: cover;
|
||||
background-repeat: no-repeat;
|
||||
background-position: center;
|
||||
background-color: rgba(0, 0, 0, 0);
|
||||
}
|
||||
|
||||
#window-box {
|
||||
padding: 64px;
|
||||
border: 2px solid @accent;
|
||||
border-radius: 30px;
|
||||
background-color: @background;
|
||||
}
|
2
config/hypr/hyprpaper.conf
Normal file
2
config/hypr/hyprpaper.conf
Normal file
|
@ -0,0 +1,2 @@
|
|||
preload = ~/Pictures/BG/bonzai.jpg
|
||||
wallpaper = eDP-1, ~/Pictures/BG/bonzai.jpg
|
242
config/hypr/main.conf
Normal file
242
config/hypr/main.conf
Normal file
|
@ -0,0 +1,242 @@
|
|||
# Plugins
|
||||
plugin {
|
||||
touch_gestures {
|
||||
# default sensitivity is probably too low on tablet screens,
|
||||
# I recommend turning it up to 4.0
|
||||
sensitivity = 20.0
|
||||
}
|
||||
}
|
||||
|
||||
# See https://wiki.hyprland.org/Configuring/Monitors/
|
||||
monitor=eDP-1,1920x1200@60,0x0,1
|
||||
|
||||
exec-once = $HOME/.config/lisgd/config &
|
||||
|
||||
# See https://wiki.hyprland.org/Configuring/Keywords/ for more
|
||||
|
||||
# Execute your favorite apps at launch
|
||||
exec-once = bash -c "sleep 3; XDG_DATA_DIRS=$kora nm-applet"
|
||||
exec-once = bash -c "sleep 4; blueberry-tray"
|
||||
exec-once = bash -c "sleep 5; nextcloud --background"
|
||||
|
||||
exec-once = eww daemon
|
||||
exec-once = eww open left-bar
|
||||
exec-once = eww open notif-panel
|
||||
exec-once = eww open quick-settings-toggle
|
||||
|
||||
# sometimes waybar starts after and stops me from pressing eww buttons
|
||||
exec-once = bash -c "sleep 0.8; eww reload"
|
||||
|
||||
exec-once = gnome-keyring-daemon --start --components=secrets
|
||||
exec-once = squeekboard
|
||||
|
||||
exec-once = wofi --show drun
|
||||
exec-once = hyprpaper
|
||||
|
||||
# after boot, there are 2 bars for some reason, so I kill them and rerun the command
|
||||
exec-once = bash -c "killall -r -0 waybar && killall -r waybar; XDG_DATA_DIRS=$kora waybar"
|
||||
exec-once = swaync
|
||||
|
||||
exec-once = wl-paste --watch cliphist store
|
||||
|
||||
# OSD window
|
||||
exec-once = swayosd-server
|
||||
|
||||
# Change HandleLidSwitch to lock in logind.conf
|
||||
exec-once = swayidle -w lock $LOCK_PATH/lock.sh
|
||||
|
||||
# Special window apps
|
||||
exec-once = thunderbird # Win + T
|
||||
exec-once = spot # Win + S
|
||||
|
||||
# Some default env vars.
|
||||
env = XCURSOR_SIZE,24
|
||||
|
||||
# For all categories, see https://wiki.hyprland.org/Configuring/Variables/
|
||||
input {
|
||||
kb_layout = ca
|
||||
kb_variant = multix
|
||||
kb_model =
|
||||
kb_options =
|
||||
kb_rules =
|
||||
|
||||
follow_mouse = 1
|
||||
|
||||
touchpad {
|
||||
natural_scroll = yes
|
||||
}
|
||||
|
||||
sensitivity = 0 # -1.0 - 1.0, 0 means no modification.
|
||||
}
|
||||
|
||||
general {
|
||||
# See https://wiki.hyprland.org/Configuring/Variables/ for more
|
||||
|
||||
gaps_in = 5
|
||||
gaps_out = 5
|
||||
border_size = 2
|
||||
col.active_border = rgb(411C6C)
|
||||
#col.active_border = rgba(33ccffee) rgba(00ff99ee) 45deg
|
||||
col.inactive_border = rgba(595959aa)
|
||||
|
||||
layout = dwindle
|
||||
}
|
||||
|
||||
misc {
|
||||
disable_hyprland_logo = true
|
||||
disable_splash_rendering = true
|
||||
vfr = true
|
||||
}
|
||||
|
||||
decoration {
|
||||
# See https://wiki.hyprland.org/Configuring/Variables/ for more
|
||||
|
||||
rounding = 20
|
||||
|
||||
blur {
|
||||
enabled = true
|
||||
size = 3
|
||||
passes = 1
|
||||
}
|
||||
|
||||
drop_shadow = false
|
||||
#shadow_range = 4
|
||||
#shadow_render_power = 3
|
||||
#col.shadow = rgba(1a1a1aee)
|
||||
}
|
||||
|
||||
animations {
|
||||
enabled = yes
|
||||
|
||||
# Some default animations, see https://wiki.hyprland.org/Configuring/Animations/ for more
|
||||
|
||||
bezier = myBezier, 0.05, 0.9, 0.1, 1.05
|
||||
|
||||
animation = windows, 1, 7, myBezier
|
||||
animation = windowsOut, 1, 7, default, popin 80%
|
||||
animation = border, 1, 10, default
|
||||
animation = borderangle, 1, 8, default
|
||||
animation = fade, 1, 7, default
|
||||
animation = workspaces, 1, 6, default
|
||||
}
|
||||
|
||||
dwindle {
|
||||
# See https://wiki.hyprland.org/Configuring/Dwindle-Layout/ for more
|
||||
pseudotile = yes # master switch for pseudotiling. Enabling is bound to mainMod + P in the keybinds section below
|
||||
preserve_split = yes # you probably want this
|
||||
}
|
||||
|
||||
master {
|
||||
# See https://wiki.hyprland.org/Configuring/Master-Layout/ for more
|
||||
new_is_master = true
|
||||
}
|
||||
|
||||
gestures {
|
||||
# See https://wiki.hyprland.org/Configuring/Variables/ for more
|
||||
workspace_swipe = yes
|
||||
workspace_swipe_fingers = 3
|
||||
workspace_swipe_cancel_ratio = 0.15
|
||||
#workspace_swipe_forever = yes
|
||||
}
|
||||
|
||||
# See https://wiki.hyprland.org/Configuring/Window-Rules/ for more
|
||||
|
||||
windowrule = noborder,^(wofi)$
|
||||
windowrule = workspace special:spot,^(dev.alextren.Spot)$
|
||||
windowrule = workspace special:thunder,^(thunderbird)$
|
||||
|
||||
windowrule = float,^(org.kde.polkit-kde-authentication-agent-1)$
|
||||
windowrule = size 741 288,^(org.kde.polkit-kde-authentication-agent-1)$
|
||||
windowrule = center,^(org.kde.polkit-kde-authentication-agent-1)$
|
||||
|
||||
windowrule = size 741 288,^(org.kde.ksshaskpass)$
|
||||
windowrule = move cursor -370 -144,^(org.kde.ksshaskpass)$
|
||||
|
||||
windowrule = float,^(org.gnome.Calculator)$
|
||||
|
||||
windowrule = size 1231 950,title:^(Open Folder)$
|
||||
windowrule = float,title:^(Open Folder)$
|
||||
|
||||
windowrule = size 1231 950,title:^(Open File)$
|
||||
windowrule = float,title:^(Open File)$
|
||||
|
||||
windowrule = float,^(com.nextcloud.desktopclient.nextcloud)$
|
||||
windowrule = move cursor 0 25,^(com.nextcloud.desktopclient.nextcloud)$
|
||||
windowrule = size 400 581,^(com.nextcloud.desktopclient.nextcloud)$
|
||||
|
||||
windowrule = tile,^(photoshop.exe)$
|
||||
|
||||
# See https://wiki.hyprland.org/Configuring/Keywords/ for more
|
||||
$mainMod = SUPER
|
||||
|
||||
bind = SUPER, F, fullscreen
|
||||
|
||||
bind = $mainMod, V, exec, cliphist list | wofi --dmenu | cliphist decode | wl-copy
|
||||
|
||||
# Example binds, see https://wiki.hyprland.org/Configuring/Binds/ for more
|
||||
bind = $mainMod, Q, exec, alacritty
|
||||
bind = $mainMod, S, togglespecialworkspace, spot
|
||||
bind = $mainMod, T, togglespecialworkspace, thunder
|
||||
bind = $mainMod, C, killactive,
|
||||
|
||||
bind = $mainMod, L, exec, $LOCK_PATH/lock.sh
|
||||
bind = $mainMod SHIFT, E, exec, eww open closer && $EWW_PATH/open.sh powermenu
|
||||
bindn =, Escape, exec, $EWW_PATH/close-opened.sh
|
||||
bind = $mainMod SHIFT, SPACE, togglefloating,
|
||||
bind = $mainMod, D, exec, wofi --show drun
|
||||
bind = $mainMod, P, pseudo, # dwindle
|
||||
bind = $mainMod, J, togglesplit, # dwindle
|
||||
|
||||
# Move focus with mainMod + arrow keys
|
||||
bind = $mainMod, left, movefocus, l
|
||||
bind = $mainMod, right, movefocus, r
|
||||
bind = $mainMod, up, movefocus, u
|
||||
bind = $mainMod, down, movefocus, d
|
||||
|
||||
# Switch workspaces with mainMod + [0-9]
|
||||
bind = $mainMod, 1, workspace, 1
|
||||
bind = $mainMod, 2, workspace, 2
|
||||
bind = $mainMod, 3, workspace, 3
|
||||
bind = $mainMod, 4, workspace, 4
|
||||
bind = $mainMod, 5, workspace, 5
|
||||
bind = $mainMod, 6, workspace, 6
|
||||
bind = $mainMod, 7, workspace, 7
|
||||
bind = $mainMod, 8, workspace, 8
|
||||
bind = $mainMod, 9, workspace, 9
|
||||
bind = $mainMod, 0, workspace, 10
|
||||
|
||||
# Move active window to a workspace with mainMod + SHIFT + [0-9]
|
||||
bind = $mainMod SHIFT, 1, movetoworkspace, 1
|
||||
bind = $mainMod SHIFT, 2, movetoworkspace, 2
|
||||
bind = $mainMod SHIFT, 3, movetoworkspace, 3
|
||||
bind = $mainMod SHIFT, 4, movetoworkspace, 4
|
||||
bind = $mainMod SHIFT, 5, movetoworkspace, 5
|
||||
bind = $mainMod SHIFT, 6, movetoworkspace, 6
|
||||
bind = $mainMod SHIFT, 7, movetoworkspace, 7
|
||||
bind = $mainMod SHIFT, 8, movetoworkspace, 8
|
||||
bind = $mainMod SHIFT, 9, movetoworkspace, 9
|
||||
bind = $mainMod SHIFT, 0, movetoworkspace, 10
|
||||
|
||||
# Scroll through existing workspaces with mainMod + scroll
|
||||
bind = $mainMod, mouse_down, workspace, e+1
|
||||
bind = $mainMod, mouse_up, workspace, e-1
|
||||
|
||||
# Move/resize windows with mainMod + LMB/RMB and dragging
|
||||
bindm = $mainMod, mouse:272, movewindow
|
||||
bindm = $mainMod, mouse:273, resizewindow
|
||||
|
||||
# Take a screenshot
|
||||
bind =, Print, exec, bash -c 'grim -g "$(slurp)" - | swappy -f -'
|
||||
bind = $mainMod SHIFT, C, exec, wl-color-picker
|
||||
|
||||
# Volume control
|
||||
binde =, XF86AudioRaiseVolume, exec, swayosd-client --output-volume raise
|
||||
binde =, XF86AudioLowerVolume, exec, swayosd-client --output-volume lower
|
||||
bind =, XF86AudioMute, exec, swayosd-client --output-volume mute-toggle
|
||||
bind =, XF86AudioMicMute, exec, swayosd-client --input-volume mute-toggle
|
||||
|
||||
bindr = CAPS, Caps_Lock, exec, swayosd-client --caps-lock
|
||||
|
||||
# Brightness control
|
||||
binde =, XF86MonBrightnessUp, exec, swayosd-client --brightness raise
|
||||
binde =, XF86MonBrightnessDown, exec, swayosd-client --brightness lower
|
51
config/hypr/scripts/autorotate.sh
Executable file
51
config/hypr/scripts/autorotate.sh
Executable file
|
@ -0,0 +1,51 @@
|
|||
#!/usr/bin/env bash
|
||||
|
||||
# This script was forked from https://gitlab.com/snippets/1793649 by Fishonadish
|
||||
|
||||
|
||||
SCREEN="eDP-1"
|
||||
WAYLANDINPUT=("wacom-hid-52eb-finger"
|
||||
"wacom-hid-52eb-pen")
|
||||
|
||||
|
||||
|
||||
function rotate_ms {
|
||||
if [[ $(hyprctl activewindow | grep Waydroid) == "" ]]; then
|
||||
case $1 in
|
||||
"normal")
|
||||
rotate 0
|
||||
;;
|
||||
"right-up")
|
||||
rotate 3
|
||||
;;
|
||||
"bottom-up")
|
||||
rotate 2
|
||||
;;
|
||||
"left-up")
|
||||
rotate 1
|
||||
;;
|
||||
esac
|
||||
elif [[ $(hyprctl monitors | grep "transform: 0") == "" ]]; then
|
||||
rotate 0
|
||||
fi
|
||||
}
|
||||
|
||||
function rotate {
|
||||
TARGET_ORIENTATION=$1
|
||||
|
||||
echo "Rotating to" $TARGET_ORIENTATION
|
||||
|
||||
hyprctl keyword monitor $SCREEN,transform,$TARGET_ORIENTATION
|
||||
|
||||
for i in "${WAYLANDINPUT[@]}"
|
||||
do
|
||||
hyprctl keyword device:"$i":transform $TARGET_ORIENTATION
|
||||
done
|
||||
|
||||
/home/matt/.config/lisgd/config &
|
||||
}
|
||||
|
||||
while IFS='$\n' read -r line; do
|
||||
rotation="$(echo $line | sed -En "s/^.*orientation changed: (.*)/\1/p")"
|
||||
[[ ! -z $rotation ]] && rotate_ms $rotation
|
||||
done < <(stdbuf -oL monitor-sensor)
|
10
config/hypr/scripts/laptop-mode.sh
Executable file
10
config/hypr/scripts/laptop-mode.sh
Executable file
|
@ -0,0 +1,10 @@
|
|||
#!/usr/bin/env bash
|
||||
|
||||
gsettings set org.gnome.desktop.a11y.applications screen-keyboard-enabled false
|
||||
|
||||
brightnessctl -d tpacpi::kbd_backlight s 2
|
||||
|
||||
killall -r autorotate.sh
|
||||
killall -r evtest
|
||||
|
||||
eww update tablet-ts=false
|
16
config/hypr/scripts/lose-focus.sh
Executable file
16
config/hypr/scripts/lose-focus.sh
Executable file
|
@ -0,0 +1,16 @@
|
|||
#!/usr/bin/env bash
|
||||
|
||||
while true
|
||||
do
|
||||
while killall -0 .blueman-manage > /dev/null 2>&1
|
||||
do
|
||||
if bluetoothctl show | grep Powered | grep -q yes; then
|
||||
if [[ $(hyprctl activewindow | grep blueman-manager) == "" && $(hyprctl clients | grep blueman-manager) != "" ]]; then
|
||||
killall .blueman-manage
|
||||
break
|
||||
fi
|
||||
sleep 0.1
|
||||
fi
|
||||
done
|
||||
sleep 0.1
|
||||
done
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Add table
Reference in a new issue