mirror of https://github.com/jarun/nnn.git
Compare commits
1974 Commits
Author | SHA1 | Date |
---|---|---|
Arun Prakash Jana | 0f10bd6cdc | |
Arun | e27d059552 | |
NRK | 4f3662cf88 | |
Arun | 9e95578c22 | |
NRK | 78b9677abd | |
Arun Prakash Jana | 55137600e0 | |
Arun Prakash Jana | be6988d1c8 | |
Arun Prakash Jana | 191e77ec5d | |
Arun Prakash Jana | 46b5255814 | |
Arun | 2fb7490bf0 | |
Arun | d61c983dd0 | |
NRK | e60be2eaa2 | |
NRK | 72ee94ed6e | |
Oktay Imanzade | b20886a29c | |
Arun | ad04944bdf | |
François Bechet | 133c0d329b | |
Arun | 5853ac8e48 | |
Martin Ziemer | 28d993a8e8 | |
Arun | 22aa1455a6 | |
KlzXS | 7806d5d371 | |
Arun | 5456ba4582 | |
c79cea05 | 297b85492f | |
Arun Prakash Jana | f71b1309a9 | |
Arun | eb66598145 | |
KlzXS | 3d6777920a | |
Arun | 4a9587a5e6 | |
KlzXS | b392dd3723 | |
Arun | 0f62c6258a | |
João F. (BeyondMagic/koetemagie) | 2a442ec30c | |
Michel DHOOGE | 5b05c8b9b1 | |
90 | eb3888cb09 | |
Arun Prakash Jana | 94aeaccdbd | |
NRK | 0738f39cf0 | |
Antonio Mancera Gamez | e76d7bbf1d | |
Arun | f2a8648861 | |
Arun | 82f9e544f2 | |
me | 3d2caf861d | |
João F. (BeyondMagic/koetemagie) | eb775914af | |
Arun | 5595d93d29 | |
Arun | bb650eb9dd | |
me | ab718387c2 | |
Jeff Davis | 3849430ebc | |
Arun | f2a909dafd | |
Arun | 404eed5fc7 | |
me | 9aaf9491ad | |
Arun | 485079d3ec | |
me | bca441e00f | |
NRK | 60eabb6170 | |
NRK | 3665541dac | |
Arun | 744a7554ef | |
blissful | c0b3cc8689 | |
blissful | 703d349389 | |
Arun Prakash Jana | 9259170afd | |
Arun | 2f22afcacc | |
luukvbaal | 4009e211f3 | |
Luuk van Baal | 3160442f0c | |
Abhinav Lakhani | 9ff81ca1f9 | |
CronyAkatsuki | 8e8289373a | |
Arun | 1051d7213d | |
Luuk van Baal | f8f6d6a482 | |
Arun | 7f63bef4d6 | |
black | bfb46159a1 | |
Arun | f3397d5ea4 | |
NRK | 336ec8be5d | |
J-Kappes | afe84862ff | |
Arun | 3176eaa85c | |
NRK | 4d5e29c3dd | |
NRK | 6d6fc3419e | |
Arun Prakash Jana | 9b921761b6 | |
Arun | 09bf8fe469 | |
blissful | 3b3ad9ccc6 | |
Arun Prakash Jana | dd07aeb703 | |
Arun Prakash Jana | 9c7c7284c0 | |
Arun | ba439084c5 | |
Xerillic | 06d8da9052 | |
Arun | ed59aa2ac3 | |
umaranis | a06af824ee | |
Xerillic | 66447d52a7 | |
Syed Umar Anis | 547508aa78 | |
Arun Prakash Jana | d72ab3497a | |
Arun Prakash Jana | 2472554e9a | |
Arun Prakash Jana | 785dd3ddf1 | |
Arun Prakash Jana | 33126ee813 | |
Arun | d8c1c99e45 | |
Syed Umar Anis | b28f209c84 | |
Arun | 1ba85825c5 | |
Arun | 66f636de13 | |
Tadeas Uhlir | e500179188 | |
Quan Tong | d220c50773 | |
Arun Prakash Jana | 186f9d01ea | |
Arun Prakash Jana | 693ba757c0 | |
Arun Prakash Jana | 3539e5c1b1 | |
Arun | d65a095d9b | |
ANtlord | dedf0554e5 | |
Arun | b835cfcc2a | |
Anomalocaridid | 80bbf76b5b | |
Anomalocaridid | 5723023491 | |
Anomalocaridid | 280068c5da | |
Arun | 53e4fec75b | |
NRK | db8b61866b | |
Arun | 26d5b5c614 | |
Arun | 899fd5b4cf | |
JingMatrix | e6ce7a614e | |
NRK | 5e3ee08e64 | |
NRK | 4c2ce0a84d | |
Arun | 0dfc6881b4 | |
Luuk van Baal | 05990dc9e5 | |
Arun | fb6e7403cf | |
NRK | b2b830e69d | |
Arun | 4149a2619d | |
Aseem Athale | aed2725cb3 | |
Arun | 04d9f6738d | |
Arun | e013a867da | |
Arun | ed58e07a98 | |
NRK | 16899bda53 | |
Arun | 4c0305f11c | |
leo-arch | 4babedc3e4 | |
NRK | ddcf331205 | |
Delgan | bd4a4454fe | |
Arun | aaf60b93d7 | |
Arun | 145ea41490 | |
Arun | 29779acc57 | |
Delgan | a7262eb4ee | |
Jasper | fb3a648756 | |
UnleashedMarf | 9be3ee9abf | |
UnleashedMarf | d873eb393d | |
Arun Prakash Jana | efd5bc9db1 | |
Arun | 737ebaa9ef | |
J. Brock | 95183fbef8 | |
Arun | fe96bd6bc7 | |
Luuk van Baal | 20e944f5e5 | |
Arun Prakash Jana | 5d81aeb477 | |
Arun | 8fd1822ca6 | |
NRK | 20725b0b4d | |
Arun | 6a8d74a43a | |
Luuk van Baal | d3b5d0e49d | |
musjj | 432b0755d3 | |
Arun | 621dbba02e | |
spfanning | 63891578d7 | |
Arun Prakash Jana | 8a1dce888a | |
Arun Prakash Jana | 9319b638e7 | |
Arun Prakash Jana | 6dd8cf8b4d | |
Arun | 18b5371d08 | |
Kian-Meng Ang | 3d1bc6e8e5 | |
Arun | 79007074f7 | |
yosh | 98d3b2135d | |
Arun | a3759abd4e | |
NRK | 57882ffab7 | |
Arun Prakash Jana | c4678e3116 | |
Arun | 03ae86cca4 | |
Arun | 15e55f5e18 | |
Arun | 2af79c9ad2 | |
Henri Bourcereau | eaffd311d4 | |
NRK | 003228afba | |
birik | 8b8e3eb522 | |
Arun | 9656c809d2 | |
Henri Bourcereau | 69882b3bff | |
NRK | 3a30211e6c | |
Arun | 2a38132012 | |
NRK | 8dbd9da0cc | |
NRK | a59a91c312 | |
amalgame21 | 1dc4c96139 | |
Arun | 9503703517 | |
Luuk van Baal | 675e50c941 | |
Arun | a4745272db | |
Jacob Moena | 2dc7f19be0 | |
NRK | bc6a09475d | |
Arun Prakash Jana | b874da395c | |
Arun | b49cc28d80 | |
NRK | 8c23c3da4e | |
Arun | f1c85b977a | |
NRK | 4867fa2bc7 | |
NRK | 9cc4b66868 | |
NRK | 8ad5c87107 | |
Arun | 9357825b34 | |
Luuk van Baal | fc26493602 | |
Arun | ade477e705 | |
Luuk van Baal | 08d2ba0b5d | |
Arun Prakash Jana | bbfb16db42 | |
Arun | d7bfe38728 | |
Luuk van Baal | 80c07741e5 | |
Arun | 3739aab578 | |
Nizamuddin Sulieman | 70204a2d0f | |
Nizamuddin Sulieman | 1ad6d30a36 | |
Nizamuddin Sulieman | 0ac8b7aa54 | |
Arun Prakash Jana | 58b77411c8 | |
Arun | d0631707fc | |
Fernando Ramos | c4c720a59a | |
Arun | 326e76b9d0 | |
Luuk van Baal | 778d6617b1 | |
Arun Prakash Jana | 33827109d5 | |
Arun Prakash Jana | 4f95796ede | |
Arun Prakash Jana | b80e047d50 | |
Arun Prakash Jana | ad4ecb19cb | |
Arun Prakash Jana | 03e0531e81 | |
Arun | 786ecf9fc2 | |
Arun | 1a5a7da8eb | |
Arun | d4575e99c8 | |
NRK | ca8fcf454a | |
KlzXS | 867726d870 | |
KlzXS | 7abfb77a13 | |
KlzXS | 827e84a56f | |
KlzXS | 8d21e5e832 | |
Arun Prakash Jana | 6b94911bc9 | |
Arun Prakash Jana | 653cab9dff | |
Arun Prakash Jana | f9295780ef | |
Arun Prakash Jana | cac5b9ba33 | |
Arun Prakash Jana | df05f593de | |
Arun Prakash Jana | 243301603e | |
Arun | f9281c8eab | |
Arun | 428c652d36 | |
KlzXS | 8a1e32d9eb | |
KlzXS | 1a2f783b75 | |
KlzXS | 6c23fdfd5f | |
Arun | fef3c673cd | |
NRK | 1887cd1a77 | |
Arun | 12aedd521d | |
NRK | cf68675478 | |
Arun | 2b6fb3f388 | |
Léo Villeveygoux | dac5fb0af9 | |
Arun Prakash Jana | 789449a464 | |
Arun | fa62b08243 | |
Arun Prakash Jana | dd214c50f3 | |
NRK | fb5b2e5e64 | |
Raffaele Mancuso | c9b384f009 | |
N-R-K | 2000ed5080 | |
8B411 | a51437ff16 | |
Arun Prakash Jana | e236bd0b3a | |
Raffaele Mancuso | 1b5cfbca3d | |
Arun Prakash Jana | 1688b07d0e | |
Arun | 4d54490433 | |
KlzXS | 87627a6e08 | |
Arun Prakash Jana | 17ed380b57 | |
Arun Prakash Jana | 38d7090e64 | |
Arun Prakash Jana | 824e7a2c18 | |
Arun Prakash Jana | 2e84716e76 | |
Arun Prakash Jana | e8bc59a816 | |
Arun Prakash Jana | 32a6a63f44 | |
Arun Prakash Jana | cf46da60d9 | |
Arun Prakash Jana | 1a04e813be | |
Arun Prakash Jana | 02dec98bf8 | |
Arun Prakash Jana | 608fbb4ad7 | |
Arun Prakash Jana | d4c3e52f2f | |
Arun Prakash Jana | 93de728eab | |
Arun Prakash Jana | c9dbae0586 | |
Arun Prakash Jana | b6bfc740ce | |
Arun Prakash Jana | 28ea6e0f36 | |
Arun Prakash Jana | 2a673b4eb1 | |
Arun Prakash Jana | cd145b982d | |
Arun Prakash Jana | 92a0158f93 | |
Arun Prakash Jana | 0c234060bf | |
Arun | 07c5590db3 | |
Sijmen J. Mulder | 2fc9d518d1 | |
Arun Prakash Jana | 1de825b5bb | |
Arun Prakash Jana | fbf9279973 | |
Arun Prakash Jana | 7330e6642b | |
Darukutsu | 4bb7ffcd4a | |
Arun | 3359b8f7cd | |
LGTM Migrator | 66fd131f2d | |
Arun | a1477c2668 | |
NRK | f13b527a93 | |
NRK | 83c4c880cc | |
daru | e7abf87c54 | |
Darukutsu | e80ba2e44a | |
Arun | 2a4231ea89 | |
NRK | 985f6537ce | |
NRK | 080a061969 | |
NRK | ff27d9ee14 | |
nblock | b511506fa3 | |
Arun | f89ba77516 | |
Arun | 0c4180f2d8 | |
NRK | e5074ebc83 | |
NRK | b00700ce4d | |
Dean G | 38b7282050 | |
Arun | 31b83ef1f0 | |
Luuk van Baal | bc4233767a | |
Arun Prakash Jana | 59eed597c2 | |
Arun Prakash Jana | de3ad1b146 | |
Christian Rackerseder | c24ede2d4a | |
Arun Prakash Jana | 0907895865 | |
Arun | 1cefc326e3 | |
Patrick | a7ce7bb36c | |
Patrick | c9c74dd753 | |
Patrick | 3dac035819 | |
Arun | f6edcc41b9 | |
pataquets | 78019a758e | |
Arun | 23f8c37094 | |
Luuk van Baal | 4f57e0df37 | |
Arun Prakash Jana | f56a8caf65 | |
Arun | 340ba19098 | |
NRK | f8ee991254 | |
Arun | d49ddd1331 | |
NRK | 29a5992dee | |
Arun | ad62463b48 | |
Luuk van Baal | 95e1d56ee4 | |
Arun Prakash Jana | a335f94d05 | |
Arun Prakash Jana | a937bc0a4c | |
Arun | 92873352e0 | |
NRK | e57bb26295 | |
Arun | 7086d030f0 | |
KlzXS | 65dec55e23 | |
Arun Prakash Jana | ab9d8bee89 | |
Arun Prakash Jana | 926c4014b3 | |
Arun Prakash Jana | a7ebc7858a | |
Arun Prakash Jana | e8acae3274 | |
Arun Prakash Jana | 21eebbb003 | |
Arun Prakash Jana | f530b2ca18 | |
Arun Prakash Jana | e298f7eeaf | |
Arun Prakash Jana | e73b57c78a | |
Arun Prakash Jana | 49a0d9d02c | |
Arun Prakash Jana | b76cea3a34 | |
Arun Prakash Jana | 83825a7d11 | |
Arun Prakash Jana | 22db656b8d | |
Arun | 07c1e8e655 | |
NRK | 61e1356fbd | |
N-R-K | f618b78866 | |
Arun Prakash Jana | f2a38b0e22 | |
Arun Prakash Jana | 0988268a61 | |
Tharindu Abeydeera | 98287158aa | |
Arun | e2e1d80d58 | |
NRK | e6b6466c49 | |
Arun Prakash Jana | f415924c7e | |
Arun Prakash Jana | ab0dc52c49 | |
Arun | f829afe60b | |
NRK | fe9c1bbb3a | |
NRK | 63a254951d | |
Arun | aab5ab53a5 | |
NRK | 12f5faa10d | |
NRK | f1932967e2 | |
Arun Prakash Jana | 197717ce68 | |
Arun | 117025c1a4 | |
Arun | 0381db1875 | |
NRK | e98d9288d2 | |
NRK | c3a42f0d92 | |
NRK | 3b09fd1c75 | |
Luuk van Baal | 3fb9cc1e5a | |
Arun Prakash Jana | d95755cce1 | |
Arun Prakash Jana | 12b5416b2c | |
Arun Prakash Jana | a937265833 | |
Anomalocaridid | f2c7495f50 | |
Arun Prakash Jana | b0580905f2 | |
Arun Prakash Jana | b75a22f72d | |
Arun Prakash Jana | b752744ca0 | |
Arun Prakash Jana | db7cb4da1e | |
Luuk van Baal | 910763441d | |
Arun Prakash Jana | b658f324c2 | |
Arun Prakash Jana | 3f4efbefe4 | |
Arun | c09ac1c174 | |
Luuk van Baal | a3cef1611d | |
Arun | f4116a5f42 | |
Jie | a7f243beed | |
Arun Prakash Jana | 8520fe5a0a | |
Arun | a998938b9d | |
NRK | fd69fc2dca | |
NRK | 7121a6fe43 | |
happy wang | dc2cfe78cd | |
Arun | 96cfd3a41a | |
NRK | 0df6eebea0 | |
NRK | 744e9aaf70 | |
NRK | 1d347b1ce9 | |
NRK | 2df0cbd08b | |
Arun | b9a1f1747f | |
Luuk van Baal | 0ab9189bc5 | |
Arun Prakash Jana | 52f4ee5aee | |
Arun | 5ace352d2c | |
Luuk van Baal | 3e84c275ba | |
Arun Prakash Jana | 89bd541562 | |
Arun Prakash Jana | 02d48a9144 | |
Arun | c69067b502 | |
NRK | af5cdca043 | |
NRK | eb66cb5d11 | |
Arun Prakash Jana | 6c197f5f02 | |
Arun Prakash Jana | 2130e1b33a | |
Arun Prakash Jana | 0c626d49a6 | |
Arun Prakash Jana | d898d174f5 | |
Arun Prakash Jana | 581e629c20 | |
Arun Prakash Jana | 56f96c3d0a | |
Arun Prakash Jana | 51f2fde0e6 | |
Arun | 40f75e9c38 | |
Luuk van Baal | 5b5a62bb0d | |
Arun Prakash Jana | 1b31f5cf9b | |
Arun Prakash Jana | 783ea754f7 | |
Arun | c02605a907 | |
Luuk van Baal | fbd6f69f25 | |
Arun Prakash Jana | 19b2ea324a | |
Arun Prakash Jana | 03fc3b99c5 | |
Arun Prakash Jana | e104b749be | |
Arun Prakash Jana | 8fb7feb61c | |
Arun Prakash Jana | 49f21ae013 | |
Göran Gustafsson | 4baee859f8 | |
Arun Prakash Jana | de004d944e | |
Arun | 4784587024 | |
Luuk van Baal | 6fc8f63c0d | |
Arun | 88306e2d9c | |
Arun | 4c6c06b743 | |
Göran Gustafsson | 5023abe2df | |
Göran Gustafsson | 93db9bb2be | |
Arun | 46a5092eee | |
NRK | 5ae3891ee5 | |
Arun | 01ab453cff | |
Luuk van Baal | 3072aa7891 | |
Arun | 0499998e2a | |
Luuk van Baal | bb604bdf1d | |
Arun Prakash Jana | a70ad9c480 | |
Arun Prakash Jana | 10e2d37d0f | |
Arun Prakash Jana | 85be28c019 | |
Arun | d859e81444 | |
Arun | 33ec6dece4 | |
Luuk van Baal | 4c974f286c | |
N-R-K | 1e98e2e126 | |
Arun | f8b8e77be9 | |
Luuk van Baal | 0095948d8d | |
Arun Prakash Jana | d618922177 | |
Arun Prakash Jana | 4337214f50 | |
Arun Prakash Jana | 31a273fdd0 | |
Arun | c2a2a9dee7 | |
Luuk van Baal | 8cdeddeb4a | |
Arun | 772fd30fa0 | |
Luuk van Baal | ae36d30b66 | |
Arun Prakash Jana | 14e80c3872 | |
Arun Prakash Jana | 8175571952 | |
Arun Prakash Jana | 3a50be93fd | |
Arun Prakash Jana | ec7692bb9e | |
Arun | e4c2cb9fd4 | |
Arun Prakash Jana | 8d83af811f | |
Dan Baz | ef5d90f4bb | |
Arun Prakash Jana | ec076f5886 | |
Arun | 81f96ecc1e | |
luukvbaal | ed7afd2dd1 | |
Arun | ab8505efa4 | |
cain-dev | b3f16e7671 | |
Arun Prakash Jana | f6783c2065 | |
Arun | a3fbda02d7 | |
NRK | ba72fca69a | |
Arun | e1e47f909f | |
NRK | 6f332e5260 | |
Arun Prakash Jana | c23125ba50 | |
Arun Prakash Jana | 0a67c5d657 | |
Arun Prakash Jana | af94c7704f | |
Desmond Kabus | b45be9bc5b | |
Arun Prakash Jana | 18a6a010cf | |
Patrick | 4ddd048feb | |
Arun Prakash Jana | fd998b3045 | |
Arun Prakash Jana | 3f58f6111c | |
Arun | 4366247441 | |
Luuk van Baal | 7793cb8b5c | |
Arun Prakash Jana | cc965d1c2d | |
Arun Prakash Jana | dc16ca2340 | |
Arun Prakash Jana | 6b9f8f3666 | |
Arun | 15243186c5 | |
SlIdE42 | 0812c7afac | |
Arun Prakash Jana | be4460c1da | |
Arun Prakash Jana | eb42f7a948 | |
Arun Prakash Jana | 2c5cb4c5aa | |
Arun | a555a7d122 | |
NRK | d0bf2abb37 | |
Arun | 59cf883437 | |
JingMatrix | 5bc75ef4fd | |
Arun | bb875cd5e7 | |
Paolo Capriotti | 4220f4e2eb | |
Arun Prakash Jana | d66492ac10 | |
Arun Prakash Jana | 88e9122c79 | |
Arun Prakash Jana | 5745597fd5 | |
Arun | 0a7742089a | |
JingMatrix | 0a59005acd | |
Arun | 81226db24e | |
NRK | 72ecf6c4b8 | |
Arun | 675016eb55 | |
NRK | 9be6c1a5e2 | |
Arun Prakash Jana | d38841d5f3 | |
Arun | 136549b1ba | |
NRK | c3534bd7e0 | |
Arun Prakash Jana | 57d212c3ca | |
Arun Prakash Jana | 66639c6053 | |
Arun | b718d6d305 | |
Arun | 994bc80e82 | |
daru | 633a9ca8e1 | |
daru | d1de515532 | |
Darukutsu | cd2445607b | |
Darukutsu | 83b6d6aff7 | |
NRK | 2fedc92efc | |
Arun Prakash Jana | 953643b9f1 | |
Arun | 816680ed01 | |
NRK | a8e9d279ac | |
Arun | cb410e25d8 | |
NRK | 799b8fd378 | |
Arun | 30bd6a4e33 | |
KlzXS | 184f134c9e | |
Arun Prakash Jana | 23b54ba0cf | |
Arun | 866612bfda | |
NRK | ff1c1eb2e1 | |
Arun | fbb2172627 | |
NRK | 24db74fd7b | |
NRK | ffd0468f67 | |
Arun Prakash Jana | e67587204b | |
Arun Prakash Jana | aa2147f3ef | |
Arun Prakash Jana | e140e34483 | |
Arun Prakash Jana | fe4ea8a029 | |
Arun | bfa2d4fce5 | |
Luuk van Baal | ecad3e0524 | |
Arun | b8b0bab426 | |
Arun | 9c6ce560f1 | |
Anomalocaridid | efa960d022 | |
lwnctd | 49aa4dabf1 | |
Arun | 2eadf35fa0 | |
NRK | 04181084c0 | |
Arun | dcf3a35cd5 | |
NRK | e2b856904d | |
Arun Prakash Jana | 693df568e0 | |
Arun | 3368a7905b | |
NRK | 02d6feb9b9 | |
NRK | 1608c8763f | |
NRK | 78c0d54400 | |
Arun | e44f8d3fcc | |
Arun | 282266705e | |
Patrick | fe0608116a | |
Arun Prakash Jana | 0fb7a25612 | |
Arun Prakash Jana | b69f838fb8 | |
Luuk van Baal | beafeaaea2 | |
Luuk van Baal | a3d660b673 | |
NRK | ac86fbed0f | |
Luuk van Baal | 48bcc929e8 | |
Luuk van Baal | 06bf4f5dce | |
KlzXS | 3be2dd8390 | |
NRK | ce58aab6b2 | |
NRK | 62f1004836 | |
NRK | d215a9c61d | |
NRK | c234c05b3d | |
NRK | f7298efa99 | |
NRK | 9a26739132 | |
NRK | 23edf571a7 | |
Arun Prakash Jana | 892e4c0082 | |
Arun Prakash Jana | bd6e7e8147 | |
Arun | ecfe819a73 | |
Luuk van Baal | b851b58e83 | |
Arun | 2c31615256 | |
Luuk van Baal | 95f709f86a | |
Arun | a1b15eb766 | |
Arun | 48e478bb90 | |
Luuk van Baal | 8ba43edffc | |
NRK | 7aef60a9d5 | |
Luuk van Baal | e0c1ed273f | |
Arun | 40b2250209 | |
Arun | eb62775852 | |
yeetologist | c147414bc7 | |
Arun Prakash Jana | 1e8b8d14ff | |
KlzXS | 8f2e17303e | |
Arun | 1bc234b0eb | |
NRK | bd8faa2dd8 | |
NRK | 578e6d1aaa | |
NRK | f7091f78e5 | |
Arun | c87b67e073 | |
Omar Polo | fb3d3ab0ef | |
Omar Polo | deead97e23 | |
Arun Prakash Jana | 8ec2fe7f81 | |
Arun Prakash Jana | 65eddfe7b9 | |
Arun | 2f986253e4 | |
Luuk van Baal | 1a6d54515b | |
Arun | 256f0d008f | |
KlzXS | ca9b5e04c7 | |
Arun | f3df0816d9 | |
Toni Jarjour | 8755a3c0cf | |
Arun Prakash Jana | f66183937d | |
Arun | 6178be7e06 | |
Luuk van Baal | 84bfbcf4e7 | |
Arun | 9cb0a13ffe | |
Luuk van Baal | e94f90c89a | |
Arun | 8b7feff4b6 | |
Arun | bd7f127ad9 | |
Arun | fec0479da3 | |
KlzXS | 875a4d8c23 | |
KlzXS | a300e3267f | |
Luuk van Baal | 0d657b47b9 | |
NRK | 39a3cc5309 | |
Arun | c9b9c14481 | |
Arun | 182ac51b8d | |
Luuk van Baal | 66dfa60465 | |
Luuk van Baal | 26f380f154 | |
KlzXS | 48415c5e1c | |
Arun | 1508874b5a | |
Arun | e686b94f7e | |
KlzXS | 22096ee0cd | |
Krisan Alifari | eff4bd6e67 | |
Arun | f854b3c748 | |
Luuk van Baal | 1621c0303b | |
Arun Prakash Jana | b84ad2d552 | |
Arun Prakash Jana | 07a47db8fe | |
Arun Prakash Jana | e2c4445d74 | |
KlzXS | eb769c0de5 | |
Terminator X | b56e488f1c | |
NRK | 5e6c62cd8e | |
Terminator X | b5f5b2f55c | |
Marco Cantoro | da03016c79 | |
Terminator X | bcae254ff2 | |
NRK | 65ae3abc24 | |
NRK | d2dff487e0 | |
NRK | afb7a6e9c1 | |
NRK | a47376ee04 | |
Arun Prakash Jana | bdbd182c65 | |
Arun Prakash Jana | cffcd655e9 | |
Arun Prakash Jana | 2a87694e6a | |
Arun Prakash Jana | 473cd271b5 | |
Arun Prakash Jana | 8efcc24e0e | |
Arun Prakash Jana | aa8baa3d91 | |
Avimitin | 254fd9b7a3 | |
Terminator X | 684a8c7b99 | |
Alexis Praga | e3e4159e11 | |
Arun Prakash Jana | 856896f55d | |
Terminator X | b72090c9a3 | |
Arun Prakash Jana | 4d864d438f | |
Luuk van Baal | de017b7aa2 | |
Arun Prakash Jana | f4f78276e2 | |
Terminator X | b411dfe1ba | |
KlzXS | 7857b7bc5a | |
KlzXS | 1022340aa1 | |
KlzXS | 73ef170da7 | |
Terminator X | 0c0afd4799 | |
Luuk van Baal | fa9067afd4 | |
Arun Prakash Jana | cb5aefa59a | |
Arun Prakash Jana | 00c73512b9 | |
Luuk van Baal | 2801832c4d | |
Terminator X | 5f76b69c36 | |
NRK | dd7c13dd77 | |
Terminator X | f3e027c283 | |
Luuk van Baal | a0fcd78df2 | |
KlzXS | bc69c968be | |
Arun Prakash Jana | 53fbab1f44 | |
Arun Prakash Jana | 24b71bcf1f | |
Arun Prakash Jana | 12fa5344cf | |
Arun Prakash Jana | d5d559ae7f | |
Arun Prakash Jana | acfec62a13 | |
Terminator X | 4dc70f4a3f | |
Arun Prakash Jana | a06ff83c22 | |
Sacha Telgenhof | 44b983f71e | |
Arun Prakash Jana | 9c36f0df34 | |
Arun Prakash Jana | 3490a959be | |
Arun Prakash Jana | c611720cba | |
Arun Prakash Jana | be549f330a | |
An Phung | e20cfd67a1 | |
Arun Prakash Jana | 3091a6f240 | |
Arun Prakash Jana | 3acbc65adb | |
Terminator X | 98585153cc | |
Terminator X | 57bae766ea | |
luukvbaal | e9dbadd465 | |
Luuk van Baal | 17bf7c97f6 | |
Terminator X | 1020f37320 | |
Luuk van Baal | 151312eb37 | |
Terminator X | 2435263052 | |
Terminator X | 831b434021 | |
Luuk van Baal | c48691fe3d | |
KlzXS | b492dfd7ca | |
Terminator X | fa7c19c409 | |
NRK | 8a1a5db92a | |
Arun Prakash Jana | 7477bd15bb | |
Arun Prakash Jana | 74b779abc9 | |
Arun Prakash Jana | 2f6c180433 | |
Arun Prakash Jana | 79b3688e49 | |
Terminator X | d772223e1f | |
Luuk van Baal | 541b936bcf | |
Arun Prakash Jana | e74aa95e3f | |
Arun Prakash Jana | fc86152fa2 | |
Terminator X | 1723aeb470 | |
Max Schillinger | 1c9ecd781c | |
Max Schillinger | f39ee39a36 | |
Arun Prakash Jana | 046d676a73 | |
Terminator X | f3e0f23718 | |
Luuk van Baal | 07c8089eaf | |
Terminator X | 2c82c77a05 | |
Luuk van Baal | 52d8aa0945 | |
Terminator X | a447c12866 | |
Luuk van Baal | d96a7bc2b7 | |
Arun Prakash Jana | ffe472ac32 | |
CantoroMC | bfc493c753 | |
luukvbaal | 532532704e | |
CantoroMC | 2a6cc41972 | |
Terminator X | 5bf9b52beb | |
Arun Prakash Jana | aea97cf3a7 | |
Arun Prakash Jana | 27e1eb54c4 | |
Arun Prakash Jana | e7aec90889 | |
Jakob Beckmann | 7f84fbc8a0 | |
Arun Prakash Jana | 9df7e5f03e | |
Arun Prakash Jana | 359d7bc29c | |
Arun Prakash Jana | fa7cef2df7 | |
Assaf Ben-Amitai | d34741107a | |
Assaf Ben-Amitai | 7de52ff890 | |
Arun Prakash Jana | 51829c8027 | |
Arun Prakash Jana | 49be2cfcd1 | |
Arun Prakash Jana | ab0ab2b5f4 | |
Daniel Eklöf | 0556ac14ec | |
Terminator X | 64c2c68bd0 | |
Luan Belem Rivello | f9cf6dad48 | |
Arun Prakash Jana | c974690482 | |
Arun Prakash Jana | 742759f32d | |
Terminator X | ad968b88da | |
joelazar | dba6eeb431 | |
Arun Prakash Jana | 55fc0c500b | |
Arun Prakash Jana | a62dbf093a | |
Arun Prakash Jana | 900513710f | |
Arun Prakash Jana | 6243de06f4 | |
Arun Prakash Jana | e11cbc289a | |
elder-n00b | e4813f06c1 | |
Arun Prakash Jana | 6c5eab5e55 | |
luukvbaal | ad6b6bd3df | |
CantoroMC | a65055fc32 | |
Arun Prakash Jana | 6c3a3dbc15 | |
CantoroMC | 43da9a9c46 | |
Arun Prakash Jana | 78ea6702f7 | |
Terminator X | 0aed67f329 | |
Luuk van Baal | 82d1510213 | |
Arun Prakash Jana | 983d689a05 | |
0xACE | 9d4330e382 | |
Arun Prakash Jana | 86648ab391 | |
Arun Prakash Jana | 46294e9f3d | |
Terminator X | 840fb75208 | |
Luuk van Baal | b5750c9e38 | |
Luuk van Baal | 2b45c1be55 | |
Luuk van Baal | b7c6fede5f | |
Arun Prakash Jana | 943a7c13ac | |
Arun Prakash Jana | 7cbc79a5fc | |
Arun Prakash Jana | 0b07b77e85 | |
Arun Prakash Jana | e4c1abb6b8 | |
Arun Prakash Jana | bf2b8d8c84 | |
Arun Prakash Jana | fc00faf7d0 | |
Arun Prakash Jana | 42061b0399 | |
Arun Prakash Jana | b2c99b9e4e | |
Arun Prakash Jana | 06e2676421 | |
Arun Prakash Jana | 97ac88dec2 | |
Arun Prakash Jana | e146ad0d7a | |
Arun Prakash Jana | 59d90aa2ce | |
Arun Prakash Jana | 1df63a78e4 | |
Arun Prakash Jana | db1efba256 | |
Arun Prakash Jana | 49ee5b21e7 | |
Arun Prakash Jana | 62a0486480 | |
Terminator X | 2c32f24073 | |
Nikolay Korotkiy | f8aaf3b34c | |
Arun Prakash Jana | 7d17cf3f63 | |
Arun Prakash Jana | 87380732dc | |
Terminator X | 1d5efa7074 | |
NRK | 5fcd3d1198 | |
Arun Prakash Jana | b54f771a44 | |
Terminator X | 23a806864f | |
NRK | f3c29fe81a | |
Arun Prakash Jana | 88e38f1efc | |
Arun Prakash Jana | 6ba0a8357f | |
Arun Prakash Jana | 8cebc69e71 | |
Arun Prakash Jana | f6856f61f7 | |
Arun Prakash Jana | f1dbb9622d | |
Terminator X | 0db988b9b2 | |
jcromero | 258a5846f7 | |
Arun Prakash Jana | d80fdf335b | |
Arun Prakash Jana | e2545f9596 | |
Arun Prakash Jana | 25fab4cb2e | |
N-R-K | 3a98dfb0b0 | |
Arun Prakash Jana | 0150c69844 | |
Arun Prakash Jana | b561772ada | |
Arun Prakash Jana | ad163fb574 | |
Arun Prakash Jana | bc5b39d54c | |
Arun Prakash Jana | 14663b964b | |
Arun Prakash Jana | 3f07a8ca76 | |
Jonathan Rash | 4b4355c733 | |
Arun Prakash Jana | 7b31a356d2 | |
Arun Prakash Jana | 9972c4bdb0 | |
Arun Prakash Jana | c470143113 | |
Arun Prakash Jana | 3b5800fc7a | |
Arun Prakash Jana | 29a7a25445 | |
Arun Prakash Jana | 6f14190e6d | |
Arun Prakash Jana | d54bc230f6 | |
Arun Prakash Jana | e31f71285d | |
Arun Prakash Jana | 1e182a1fe5 | |
Arun Prakash Jana | f7aa4ed324 | |
Arun Prakash Jana | 0ef34a930c | |
Arun Prakash Jana | 07b627a725 | |
Arun Prakash Jana | a911b3044a | |
Arun Prakash Jana | 26f44f0dfc | |
Arun Prakash Jana | fa0f9ddc93 | |
Arun Prakash Jana | 3ef50f06f8 | |
Arun Prakash Jana | d40dbfd69a | |
Arun Prakash Jana | 8af773eb0d | |
Arun Prakash Jana | 8ad807d4a9 | |
Arun Prakash Jana | 4ec87e3021 | |
Arun Prakash Jana | 0159c08602 | |
Arun Prakash Jana | 064f5ea998 | |
Arun Prakash Jana | 9526fb7612 | |
Arun Prakash Jana | 61d8a29d84 | |
Arun Prakash Jana | cef9bd289f | |
Arun Prakash Jana | b3ef30a8ba | |
Arun Prakash Jana | 96f2dfa8a5 | |
Arun Prakash Jana | 60f310160a | |
Arun Prakash Jana | baca4693ec | |
Terminator X | e94ac0b91b | |
KlzXS | b5d1a1b036 | |
KlzXS | c0dceb18c6 | |
Arun Prakash Jana | d9db6b045c | |
Arun Prakash Jana | 5f5ee10e94 | |
Arun Prakash Jana | facdc5fdeb | |
Piña Colada | 1269dd2695 | |
Luuk van Baal | ddf845be88 | |
Piña Colada | c482cf54f0 | |
Luuk van Baal | 4abced6142 | |
Piña Colada | 77c16ac143 | |
Luuk van Baal | 36ddbac10a | |
Arun Prakash Jana | d4a4c72e00 | |
Piña Colada | a7aae40069 | |
Luuk van Baal | fe07ae35f2 | |
Piña Colada | a7603ba1f2 | |
Luuk van Baal | a199156cae | |
Piña Colada | ce8b9fdb2f | |
1bman | 99bd80137d | |
Piña Colada | 2fda5c78e0 | |
KlzXS | c39e54b288 | |
Arun Prakash Jana | 1729a10ef4 | |
Arun Prakash Jana | 96fb61a6a2 | |
Piña Colada | 15b60a80ad | |
Arun Prakash Jana | 04a806dc09 | |
Toni Jarjour | 1607200a75 | |
Arun Prakash Jana | 63ef6d7340 | |
Arun Prakash Jana | 73a175cc39 | |
Arun Prakash Jana | d1df9343c6 | |
Arun Prakash Jana | e7f73d95ce | |
Arun Prakash Jana | eae60c3048 | |
KlzXS | 20e0c49292 | |
Arun Prakash Jana | 7ce5bbcdf7 | |
Arun Prakash Jana | 94c399e2cf | |
Arun Prakash Jana | d9f988e7ed | |
Arun Prakash Jana | 983babc5f6 | |
Arun Prakash Jana | c597f3be9b | |
Arun Prakash Jana | 0e8819fea8 | |
Arun Prakash Jana | 2ffb0f7c79 | |
Arun Prakash Jana | 556941c2b2 | |
Arun Prakash Jana | 4f297fa147 | |
Arun Prakash Jana | 9f86015c16 | |
Arun Prakash Jana | c0ed6d1d04 | |
Arun Prakash Jana | b626cfa00f | |
Arun Prakash Jana | 3e91c2c977 | |
Arun Prakash Jana | 8f3785f2e5 | |
Arun Prakash Jana | d5359f0455 | |
Arun Prakash Jana | 17bb0cfb52 | |
Arun Prakash Jana | e8f0c53287 | |
Arun Prakash Jana | 96cbb4ff84 | |
Arun Prakash Jana | 35aa864554 | |
Arun Prakash Jana | 825effb264 | |
Michael Lan | b2e7f7794c | |
luukvbaal | 02b5b15001 | |
Arun Prakash Jana | 640a56e1cc | |
Arun Prakash Jana | 239c7e7970 | |
Arun Prakash Jana | 0b99247774 | |
Arun Prakash Jana | 1590103ab7 | |
Arun Prakash Jana | 3db1dfd17f | |
Arun Prakash Jana | 0884ad4af9 | |
Arun Prakash Jana | 745a30ccb5 | |
Arun Prakash Jana | a007fe8493 | |
Arun Prakash Jana | 4c66a8c0c3 | |
Arun Prakash Jana | 3834d75d77 | |
Arun Prakash Jana | e256353fbf | |
Arun Prakash Jana | 54258749e1 | |
Arun Prakash Jana | 361521b769 | |
Arun Prakash Jana | 16a15fc976 | |
Arun Prakash Jana | 06c5b17c02 | |
Arun Prakash Jana | 8c116eea2c | |
Arun Prakash Jana | f4f6919c02 | |
Anna Arad | 4f977ff269 | |
Arun Prakash Jana | 0dd76e7aec | |
Arun Prakash Jana | 69926a8eff | |
Arun Prakash Jana | 9a124ae935 | |
Arun Prakash Jana | 145ca91df2 | |
Arun Prakash Jana | e537c22281 | |
Piña Colada | 8238410d4c | |
Kevin Sjöberg | 8fc18fb9d6 | |
Kevin Sjöberg | f443768260 | |
Arun Prakash Jana | cbbac4728b | |
Arun Prakash Jana | 54b2eb51d5 | |
Arun Prakash Jana | 46b48cf71c | |
Arun Prakash Jana | 6d2d901a91 | |
Arun Prakash Jana | 51ac3d02c9 | |
Arun Prakash Jana | 15eed29227 | |
Arun Prakash Jana | 3b6938f782 | |
Arun Prakash Jana | f24b82a750 | |
Arun Prakash Jana | 9de941306c | |
Arun Prakash Jana | 5e34181bb3 | |
Arun Prakash Jana | d87414eb61 | |
Arun Prakash Jana | 488fe6b941 | |
Arun Prakash Jana | fb6ca79197 | |
Piña Colada | 29bce804be | |
Luuk van Baal | 7edf14139b | |
Arun Prakash Jana | e1a9aa0aa5 | |
Piña Colada | b8851bdf16 | |
Luuk van Baal | c9c0be32a8 | |
Piña Colada | 4637a5a84d | |
Luuk van Baal | 0fff92b396 | |
Piña Colada | 7b32e3bae0 | |
Luuk van Baal | 5533f152bd | |
Piña Colada | f681a5b3f1 | |
Luuk van Baal | 99e039d504 | |
Arun Prakash Jana | f03b5dd4a9 | |
Arun Prakash Jana | 2df1e64127 | |
Arun Prakash Jana | 5a6df62b1c | |
luukvbaal | c205177ac6 | |
Piña Colada | 14be56057c | |
Luuk van Baal | de430efafb | |
luukvbaal | f3eac98678 | |
Arun Prakash Jana | 29ef232301 | |
Arun Prakash Jana | 88e9171266 | |
Arun Prakash Jana | f27e93fba0 | |
Arun Prakash Jana | ccce80a1e9 | |
Arun Prakash Jana | b52c09dd23 | |
Arun Prakash Jana | bf673744fb | |
luukvbaal | 93e7995ab5 | |
Piña Colada | 6f862131e1 | |
Luuk van Baal | 40031b81ae | |
Arun Prakash Jana | 859ddf8d88 | |
Piña Colada | a79ef66abb | |
Luuk van Baal | 272e47c64a | |
Arun Prakash Jana | 6a904f7cf5 | |
Piña Colada | 63913115df | |
Luuk van Baal | cc8a21fa61 | |
Piña Colada | 2238fa9cbc | |
Luuk van Baal | e4988f0264 | |
Piña Colada | 6eda83097a | |
Luuk van Baal | b6fd7d928c | |
Piña Colada | 609b6a426a | |
Luuk van Baal | 2f9c700537 | |
Arun Prakash Jana | 6d817a41e3 | |
Arun Prakash Jana | 6f29138299 | |
Arun Prakash Jana | c54ba35ce0 | |
Arun Prakash Jana | 4ea0d70217 | |
Arun Prakash Jana | 46e1d6bdda | |
Arun Prakash Jana | 85c108a5d6 | |
Arun Prakash Jana | 6bb6ddfe8a | |
Arun Prakash Jana | 4bc8e1a8be | |
Arun Prakash Jana | a6eeceec55 | |
Arun Prakash Jana | f6b14f6505 | |
Arun Prakash Jana | b397606d0a | |
Arun Prakash Jana | 462531b8c7 | |
Arun Prakash Jana | 831287c92e | |
Arun Prakash Jana | 30ee27802e | |
Arun Prakash Jana | a8c52134f6 | |
Piña Colada | 28731a10f7 | |
Luuk van Baal | 0a569496c8 | |
Arun Prakash Jana | 326d5a4fae | |
luukvbaal | 78b2170e03 | |
Arun Prakash Jana | 284a3c4866 | |
Arun Prakash Jana | 025b570e05 | |
Arun Prakash Jana | db8079f552 | |
Arun Prakash Jana | fdeba8a87e | |
Arun Prakash Jana | 1017413474 | |
Arun Prakash Jana | 53e98a9fd1 | |
Arun Prakash Jana | 88f71ff35d | |
Arun Prakash Jana | 54d760b9f5 | |
Arun Prakash Jana | 36e1544b32 | |
Luuk van Baal | b89c32b9fa | |
Arun Prakash Jana | 2bd72d1b29 | |
Arun Prakash Jana | edab98ab6d | |
Piña Colada | bb5642291c | |
Luuk van Baal | d64242aec3 | |
Arun Prakash Jana | 45ac90d5e6 | |
Piña Colada | 9a949b7c33 | |
Luuk van Baal | 88eb45944c | |
Piña Colada | 8a36196e98 | |
Luuk van Baal | 8eced6c5d4 | |
Arun Prakash Jana | cbc4587630 | |
Piña Colada | 715abc7a3f | |
Luuk van Baal | 5cc98987c5 | |
Piña Colada | a95ed82f60 | |
Luuk van Baal | 5fba2ba749 | |
Arun Prakash Jana | 31c34740bc | |
Arun Prakash Jana | 79cbcc18e1 | |
Piña Colada | db240eeeda | |
Luuk van Baal | f7e84bed70 | |
Arun Prakash Jana | 7bbacd0f0d | |
Arun Prakash Jana | 4dcefcc4d4 | |
Kabouik | 69d63ff50e | |
Arun Prakash Jana | 5e8ef070dc | |
Arun Prakash Jana | 24080569b8 | |
luukvbaal | bb37c9dd46 | |
Kabouik | b14d2311e6 | |
Arun Prakash Jana | 7a76ca8548 | |
Arun Prakash Jana | f343f315b5 | |
Arun Prakash Jana | 513b4f24a6 | |
Arun Prakash Jana | 1fabac27ba | |
Arun Prakash Jana | 3316e2acdb | |
Arun Prakash Jana | 6222cac4bf | |
Arun Prakash Jana | 177b60e6c2 | |
Piña Colada | 2ca11a34e7 | |
Piña Colada | d83acda68b | |
Luuk van Baal | 9560a91f97 | |
Luuk van Baal | 2edf59fef1 | |
Arun Prakash Jana | d46918946f | |
Arun Prakash Jana | d0b4508798 | |
Arun Prakash Jana | 0427f70c4e | |
Arun Prakash Jana | bca5763cf7 | |
lawnowner | 9cbb7f540c | |
Piña Colada | dd02afc58b | |
Luuk van Baal | 16b2f40ffe | |
Arun Prakash Jana | 6b0f308f26 | |
Arun Prakash Jana | 448a4203bc | |
Arun Prakash Jana | 04c38ecf3d | |
Arun Prakash Jana | 1b88062310 | |
Piña Colada | 9756ce4650 | |
Arun Prakash Jana | 4a4628e2fc | |
Piña Colada | 375d1057c1 | |
Marco Cantoro | d6af0d2ed4 | |
KlzXS | 56d3f2d976 | |
Arun Prakash Jana | 907616a058 | |
Arun Prakash Jana | 1f95c355a9 | |
Arun Prakash Jana | 9c5214c24a | |
Arun Prakash Jana | de80bba9db | |
Arun Prakash Jana | 466d138cc7 | |
Arun Prakash Jana | e4c3f7d739 | |
Arun Prakash Jana | 9b6e7e86bc | |
Arun Prakash Jana | b44d2c5071 | |
Arun Prakash Jana | 8575711227 | |
Piña Colada | c506da4419 | |
Luuk van Baal | a359a8152c | |
Arun Prakash Jana | c0ccf098ec | |
Luuk van Baal | a327ee4a3d | |
Arun Prakash Jana | eec6366272 | |
Arun Prakash Jana | b5654e3188 | |
Piña Colada | e075b98cfe | |
Piña Colada | f45967c4a0 | |
Luuk van Baal | 6c450bee94 | |
Arun Prakash Jana | f3fe27e694 | |
Arun Prakash Jana | e5c1b0bdd2 | |
Arun Prakash Jana | 0691c4fb47 | |
Arun Prakash Jana | da7dc8e6e2 | |
Arun Prakash Jana | 7acc9196d5 | |
Arun Prakash Jana | 4727b3baa8 | |
luukvbaal | f4eb89029c | |
Arun Prakash Jana | 69df38dfd4 | |
Arun Prakash Jana | 54aa971a6b | |
Piña Colada | 7a562d7b03 | |
Luuk van Baal | 6730c0fd01 | |
Arun Prakash Jana | b58e9fc384 | |
Arun Prakash Jana | 0d21813b11 | |
Arun Prakash Jana | 765986b916 | |
Arun Prakash Jana | 41d414c2fc | |
Arun Prakash Jana | 0eeae6ee7b | |
Arun Prakash Jana | bd47846185 | |
Arun Prakash Jana | 949f76ec16 | |
Arun Prakash Jana | d4767e6d47 | |
Piña Colada | 19a5ef8a61 | |
Luuk van Baal | d73569be73 | |
Piña Colada | 703be56930 | |
Luuk van Baal | 65e306feec | |
luukvbaal | 74785069e0 | |
Arun Prakash Jana | 2ac70152a4 | |
Arun Prakash Jana | 3ab8bf1c16 | |
KlzXS | 002758063e | |
KlzXS | 36d86a294d | |
Kabouik | c2aeb51bcc | |
luukvbaal | 5ed2998023 | |
Arun Prakash Jana | e8bebac168 | |
Arun Prakash Jana | 714d806341 | |
luukvbaal | 802a7794ae | |
Arun Prakash Jana | 163102e8ae | |
Luuk van Baal | 7a7fd5fcab | |
luukvbaal | 4ebc396250 | |
Arun Prakash Jana | 0c88d1c210 | |
luukvbaal | d998943119 | |
luukvbaal | b97e2d02ea | |
Arun Prakash Jana | eea4d34423 | |
Arun Prakash Jana | 34c3d2116a | |
Arun Prakash Jana | 1fde10b022 | |
luukvbaal | 1241a4d75d | |
akimdi | c673840d5d | |
Piña Colada | b0a985bca8 | |
Luuk van Baal | cbbefe805a | |
Arun Prakash Jana | 4648a56178 | |
Piña Colada | 59dfffd004 | |
Luuk van Baal | 15031f7d9e | |
Piña Colada | f0c64a89b8 | |
Luuk van Baal | 77640a6434 | |
Piña Colada | a629707eec | |
Luuk van Baal | ec3f754192 | |
Piña Colada | 47a779b1bf | |
luukvbaal | 48898eeb8b | |
Roland Kammerer | 5c1c732fb7 | |
Piña Colada | cd070a6228 | |
akimdi | 5f67acd8b8 | |
akimdi | 794048b306 | |
Piña Colada | c49f24c696 | |
Luuk van Baal | 14350b94a8 | |
Arun Prakash Jana | e09148e386 | |
Arun Prakash Jana | b08aa8330d | |
Arun Prakash Jana | 6d2325e18a | |
Arun Prakash Jana | 69431e49a9 | |
Arun Prakash Jana | 430833326b | |
Arun Prakash Jana | 25157592df | |
Arun Prakash Jana | 2b94c29e1d | |
Arun Prakash Jana | 30e1c54e0e | |
Arun Prakash Jana | b5015b8e6c | |
Arun Prakash Jana | f4c5b1a937 | |
Arun Prakash Jana | 5bfc868321 | |
Mischievous Meerkat | 285463253c | |
Luuk van Baal | ad4f0cbbef | |
Luuk van Baal | 1fd61ca5f5 | |
Arun Prakash Jana | ad40ae9b53 | |
Arun Prakash Jana | a482e8afe5 | |
Arun Prakash Jana | 0c55e74fb5 | |
Arun Prakash Jana | ee04215d91 | |
Mischievous Meerkat | 99a8f761cf | |
Luuk van Baal | 710e621735 | |
Luuk van Baal | eb98b9076b | |
Luuk van Baal | a5a1c7b82c | |
Arun Prakash Jana | a1cb764943 | |
Arun Prakash Jana | 903a4b3a66 | |
Mischievous Meerkat | 9a73057272 | |
Luuk van Baal | ada4695bb6 | |
Arun Prakash Jana | dc9d877941 | |
Luuk van Baal | f1f147c928 | |
Mischievous Meerkat | a0be1c33cb | |
akim | 534aa355a1 | |
Arun Prakash Jana | a44b23786f | |
Arun Prakash Jana | b3132d6398 | |
Arun Prakash Jana | f27df77777 | |
Arun Prakash Jana | edacfcc828 | |
Arun Prakash Jana | 0223d53584 | |
Arun Prakash Jana | b0fd7a5ffe | |
Arun Prakash Jana | dd5588650d | |
Arun Prakash Jana | ed23e494a9 | |
Arun Prakash Jana | a62bcd3f87 | |
Arun Prakash Jana | ed55fbd9d5 | |
Arun Prakash Jana | 98308b8444 | |
exoton | 98a0f7484a | |
Arun Prakash Jana | a6a09338a2 | |
Mischievous Meerkat | df6dbbb84c | |
Luuk van Baal | c3a472a7e2 | |
Arun Prakash Jana | 3f47c6ee55 | |
Mischievous Meerkat | da734c50da | |
Luuk van Baal | 9fcdf78643 | |
luukvbaal | 5cf723fbe4 | |
Arun Prakash Jana | 34f20ea678 | |
Mischievous Meerkat | e459d912b0 | |
Yuri Kloubakov | 1a0c9d0c90 | |
exoton | 42aa97b112 | |
luukvbaal | 832676984b | |
Rudolf Adamkovič | 655e8886f1 | |
Arun Prakash Jana | 603c1580e8 | |
Arun Prakash Jana | 6dfea38999 | |
Arun Prakash Jana | b29d898350 | |
Arun Prakash Jana | 8542f5bc33 | |
Arun Prakash Jana | ccf2927b6d | |
Arun Prakash Jana | e5d44ce223 | |
Benawi Adha | 0f4dfee6c6 | |
Arun Prakash Jana | 37fbed2fb7 | |
Arun Prakash Jana | 980fd80aa9 | |
Arun Prakash Jana | 7f5dbd11e3 | |
Arun Prakash Jana | 7c63dc8d73 | |
luukvbaal | d5dac4c686 | |
Arun Prakash Jana | 9c218d41e8 | |
Benawi Adha | b0aa1fe379 | |
Arun Prakash Jana | f602cbee07 | |
Mischievous Meerkat | 7233935109 | |
Léo Villeveygoux | 5bba7b45fa | |
Benawi Adha | f176d81ea0 | |
Arun Prakash Jana | d8e370e579 | |
Benawi Adha | c61a716e11 | |
lvgx | 1c2cb7fd31 | |
luukvbaal | f90e567a17 | |
Benawi Adha | 638676a689 | |
luukvbaal | e0822fdef4 | |
Arun Prakash Jana | 9f0a374255 | |
Arun Prakash Jana | 2f6046e6da | |
luukvbaal | 73a54e7550 | |
luukvbaal | bc59961d98 | |
luukvbaal | 9544eb91d2 | |
luukvbaal | bebad983ca | |
luukvbaal | ac29a7c166 | |
Arun Prakash Jana | 49c458517f | |
Arun Prakash Jana | 71083b0670 | |
Arun Prakash Jana | c625679d58 | |
Arun Prakash Jana | 2fc61a8f48 | |
Arun Prakash Jana | 4a45e45b30 | |
luukvbaal | fdf40df5e9 | |
Arun Prakash Jana | 943728dd14 | |
luukvbaal | 2e4aca5e6b | |
Arun Prakash Jana | a88bbe1a9c | |
luukvbaal | f596ae2359 | |
Luuk van Baal | 77cde578e0 | |
Arun Prakash Jana | 4c8e2e25b8 | |
Arun Prakash Jana | 5f0b3b74d0 | |
Arun Prakash Jana | c825a9e541 | |
Arun Prakash Jana | 381b251fd0 | |
Arun Prakash Jana | 317076b893 | |
Arun Prakash Jana | fddc5086dd | |
Arun Prakash Jana | 93ca773c59 | |
Arun Prakash Jana | 2dccb94f3f | |
Arun Prakash Jana | 12e7e2c7e0 | |
Mischievous Meerkat | 571363b0f9 | |
Rudolf Adamkovič | 02eb42b0ed | |
Arun Prakash Jana | d40137f7b3 | |
Arun Prakash Jana | 234a7e0080 | |
Mischievous Meerkat | 3c0c5951ee | |
Luuk van Baal | 7527125487 | |
Arun Prakash Jana | 519ea8347e | |
Arun Prakash Jana | 3cd93a355a | |
Arun Prakash Jana | bd95763c7a | |
luukvbaal | ac72d2c66e | |
Arun Prakash Jana | e8577baab2 | |
luukvbaal | 1571ea2b35 | |
Arun Prakash Jana | 3387f0a6ac | |
Arun Prakash Jana | e901615fcc | |
Arun Prakash Jana | 8886f1cd56 | |
Arun Prakash Jana | c7140e6758 | |
Arun Prakash Jana | 822546f285 | |
Arun Prakash Jana | 07afd45243 | |
Mischievous Meerkat | 5c47ac651f | |
Mischievous Meerkat | 4b15535983 | |
Mischievous Meerkat | 916910bd7a | |
KlzXS | 8bdd4b2e2a | |
KlzXS | 54b7dc4756 | |
KlzXS | c9c1d0d454 | |
KlzXS | a27568824e | |
Arun Prakash Jana | 7e307bc2ff | |
Mischievous Meerkat | e3c994bd36 | |
0xACE | 67962efbd5 | |
Arun Prakash Jana | 16de133fea | |
Arun Prakash Jana | 600286b627 | |
Arun Prakash Jana | 026f76f14c | |
Mischievous Meerkat | d07c4907de | |
Lucas Summers | 8a12c01da4 | |
Lucas Summers | 83232684a8 | |
Arun Prakash Jana | 118657020e | |
Mischievous Meerkat | 4178f62ece | |
uvelichitel | 3776f72af1 | |
Mischievous Meerkat | d23cc2fe15 | |
Arun Prakash Jana | 5d8738544b | |
freddii | 50386ff511 | |
Mischievous Meerkat | 86abd83dfd | |
Simone | f23452396e | |
Mischievous Meerkat | f4baa394be | |
KlzXS | 7310a9a773 | |
Robin Schneider | 25eba96466 | |
Arun Prakash Jana | c1e673b830 | |
Arun Prakash Jana | 8e92ea8ad6 | |
Mischievous Meerkat | 057c88a1e9 | |
johnnybash | 37de198303 | |
johnnybash | 4d77066b62 | |
johnnybash | a918a59856 | |
Mischievous Meerkat | 66a8b69426 | |
0xflotus | eb47a6c538 | |
Arun Prakash Jana | 18232f993d | |
Arun Prakash Jana | 12f3d0af61 | |
Mischievous Meerkat | 558048b6cd | |
kyechou | f1ea3e3ceb | |
Arun Prakash Jana | 9946b37177 | |
Arun Prakash Jana | fc3a247c31 | |
Arun Prakash Jana | 1ac4b9bd5a | |
Arun Prakash Jana | a984b6a9e8 | |
Arun Prakash Jana | a31af54c00 | |
Arun Prakash Jana | 947c4a9faf | |
Arun Prakash Jana | 4845ec72c5 | |
Arun Prakash Jana | 7afd17d1c8 | |
Arun Prakash Jana | 375df9f40b | |
Arun Prakash Jana | f4cb5c63d0 | |
Arun Prakash Jana | b54fc95c43 | |
Arun Prakash Jana | 5966927008 | |
Arun Prakash Jana | 6555dd8cee | |
Arun Prakash Jana | 2ec9103859 | |
Mischievous Meerkat | d54033089c | |
max | 9a7e27c334 | |
Mischievous Meerkat | 9270d4a044 | |
tchici | 9f3fbd93ce | |
Mischievous Meerkat | be34af5aeb | |
tchici | ea81864e03 | |
Arun Prakash Jana | 9e3bd377b0 | |
Arun Prakash Jana | a7fd4957dd | |
Arun Prakash Jana | 63315c88d2 | |
Arun Prakash Jana | 58bb63633d | |
Mischievous Meerkat | d0a7d61bd2 | |
Marco Grunert | 6f7a4f723b | |
Arun Prakash Jana | b4b3ee4868 | |
Arun Prakash Jana | 7f605ab995 | |
Arun Prakash Jana | a443a321ef | |
Arun Prakash Jana | 8735f11c58 | |
Arun Prakash Jana | d38f4b13d4 | |
Arun Prakash Jana | aefe962182 | |
Arun Prakash Jana | f6cc2e6161 | |
Arun Prakash Jana | b528bc734b | |
Arun Prakash Jana | 9e40110731 | |
Arun Prakash Jana | e6d510bed0 | |
Arun Prakash Jana | 0bfc590f90 | |
Arun Prakash Jana | 13923117dc | |
Arun Prakash Jana | 74cd15c232 | |
Arun Prakash Jana | b09adb4654 | |
Arun Prakash Jana | 7afc3eeedd | |
Arun Prakash Jana | 1c4bc318f5 | |
Arun Prakash Jana | 52b87a2492 | |
Arun Prakash Jana | c674cb5934 | |
Arun Prakash Jana | 1418ecde0d | |
Arun Prakash Jana | 8b9e0edc94 | |
Mischievous Meerkat | 7b3b41093e | |
KlzXS | 49936d1ca2 | |
KlzXS | 81953dd571 | |
KlzXS | d4c1986a95 | |
KlzXS | e8803b8b64 | |
Arun Prakash Jana | 75a4123f5a | |
KlzXS | 05bf019fbb | |
Arun Prakash Jana | d8d43ca85f | |
Arun Prakash Jana | 9f6808a35a | |
Arun Prakash Jana | 7b233c215c | |
Arun Prakash Jana | 30edbeee6c | |
Arun Prakash Jana | 0b31414c9a | |
Arun Prakash Jana | ff5685b64d | |
Mischievous Meerkat | aabbf6ddcb | |
Doug Headley | 2b3b0990cc | |
Arun Prakash Jana | 3737527ba9 | |
KlzXS | afdba193e4 | |
KlzXS | 782df96080 | |
Arun Prakash Jana | 57163ffa5d | |
Tim Adler | f3e122fc32 | |
Arun Prakash Jana | 65bffda6eb | |
Arun Prakash Jana | 56757860d4 | |
Arun Prakash Jana | 234f7ae563 | |
Arun Prakash Jana | 7b870281aa | |
Placido Fernandez | d38bed58b2 | |
Arun Prakash Jana | dbf12ed031 | |
Arun Prakash Jana | c074572748 | |
Placido Fernandez | ed53c54ba2 | |
Arun Prakash Jana | 1b1842c354 | |
Tim Gates | bfcf296334 | |
Arun Prakash Jana | d15b47ab86 | |
Arun Prakash Jana | afe0b0a7bd | |
Arun Prakash Jana | 881ea36f11 | |
Arun Prakash Jana | 43acb25255 | |
Arun Prakash Jana | 8bbe7e9896 | |
Arun Prakash Jana | 499127c698 | |
Arun Prakash Jana | 99e32f26f5 | |
Arun Prakash Jana | 04e1b03fd1 | |
Arun Prakash Jana | 5d955c772e | |
Mischievous Meerkat | 25770e8c0e | |
Arun Prakash Jana | 0581c3f1c7 | |
Arun Prakash Jana | c235c0f5c8 | |
lvgx | 78e576ae24 | |
lvgx | 6067a91ae6 | |
lvgx | d1d4c4ad22 | |
lvgx | d9c0c08698 | |
Arun Prakash Jana | b5232de642 | |
Arun Prakash Jana | 51009f8241 | |
Arun Prakash Jana | 627c5cfc36 | |
Arun Prakash Jana | 1d903a8c90 | |
Arun Prakash Jana | 55f2a0823a | |
Arun Prakash Jana | 2e870f3879 | |
Arun Prakash Jana | faddaa5c3a | |
cdarkly | 88256206d7 | |
Arun Prakash Jana | 56621705e8 | |
Arun Prakash Jana | 56dec17840 | |
Arun Prakash Jana | e25dc108bf | |
Arun Prakash Jana | d11992c8f0 | |
Arun Prakash Jana | 02b3f65dbe | |
Arun Prakash Jana | 01455b3d3a | |
Arun Prakash Jana | 07e994788a | |
Toni Jarjour | 240c0e5fed | |
Toni Jarjour | 1912cee957 | |
Dave Snider | 1fc1b8be8b | |
Arun Prakash Jana | 868c1898d3 | |
Arun Prakash Jana | 12c09e85e3 | |
Arun Prakash Jana | 2ddabf19e0 | |
Mischievous Meerkat | 578912e75e | |
0xACE | 858794fd27 | |
Arun Prakash Jana | d11b07fd01 | |
Arun Prakash Jana | 835f0c16d6 | |
Arun Prakash Jana | 055652d979 | |
Arun Prakash Jana | f21ed23273 | |
Arun Prakash Jana | 1696455a6f | |
Arun Prakash Jana | 0b0605813d | |
Arun Prakash Jana | 02bb398550 | |
FriendlyNeighborhoodShane | a8afbf89d5 | |
Arun Prakash Jana | 279f36f628 | |
Dave Snider | 3bd115ef93 | |
Dave Snider | f79af220c7 | |
Arun Prakash Jana | 2f61b0910d | |
Arun Prakash Jana | df264fa6cd | |
majjejjam | 3087c21be5 | |
lvgx | bcbe8080be | |
Jake Secunda | d37356a936 | |
Gregory Anders | 1afdd48f5d | |
Arun Prakash Jana | d788566268 | |
Arun Prakash Jana | 6627f8f272 | |
Arun Prakash Jana | 9c20f43410 | |
Arun Prakash Jana | 551e9ca7e5 | |
Arun Prakash Jana | 351ddb1dd7 | |
Arun Prakash Jana | faea2915f4 | |
Arun Prakash Jana | ba2040afec | |
Arun Prakash Jana | 6a4ff8b825 | |
Arun Prakash Jana | b5c7d41d9b | |
Arun Prakash Jana | 1e72069378 | |
Arun Prakash Jana | cc82403be4 | |
Arun Prakash Jana | 5db2298956 | |
Arun Prakash Jana | d86810a425 | |
KlzXS | a85467d462 | |
Arun Prakash Jana | 1998b88c14 | |
Arun Prakash Jana | 8a82c58a2a | |
Arun Prakash Jana | 5fa16dbd15 | |
Anarchiste | 7d672411bb | |
Arun Prakash Jana | 9459b15672 | |
Arun Prakash Jana | fbd5e77ec1 | |
Jana | 0c93b170c8 | |
ucs | 52d3d514ce | |
Jana | fb454a5046 | |
Jana | dc488857e1 | |
ucs | dd6976dfad | |
CodeforEvolution | 6f9571a805 | |
Arun Prakash Jana | 90e0d5e3d6 | |
Arun Prakash Jana | aa8769ecee | |
Arun Prakash Jana | 966fe839ee | |
Arun Prakash Jana | c566afd819 | |
Arun Prakash Jana | 1fecdb2393 | |
Arun Prakash Jana | 7dbf1ca3b7 | |
Arun Prakash Jana | 75c34d5f68 | |
Arun Prakash Jana | 5e3a793480 | |
Arun Prakash Jana | 8ddc659df8 | |
Arun Prakash Jana | f712441eda | |
Arun Prakash Jana | a1b43ae830 | |
Arun Prakash Jana | 8c2e1726ba | |
Arun Prakash Jana | 13ccf25551 | |
Arun Prakash Jana | b1ff36eb05 | |
Arun Prakash Jana | 11cc2797bb | |
Arun Prakash Jana | 3a61b3fc7f | |
Arun Prakash Jana | 66bb5a67d6 | |
Arun Prakash Jana | ef2d5a54d2 | |
Arun Prakash Jana | 42fd2a4d13 | |
Arun Prakash Jana | ae961da157 | |
Arun Prakash Jana | ccfccb7187 | |
Arun Prakash Jana | 8d94809897 | |
Arun Prakash Jana | 33953147d6 | |
Arun Prakash Jana | f03ddb587c | |
Arun Prakash Jana | 2fbb6ae35f | |
Arun Prakash Jana | b3f2e47173 | |
Arun Prakash Jana | b948423a80 | |
Arun Prakash Jana | 359b6f7a37 | |
Arun Prakash Jana | d5e303beb7 | |
Arun Prakash Jana | 83fa6a0ff6 | |
Arun Prakash Jana | 110a4eb108 | |
Arun Prakash Jana | 9bad3c9399 | |
Arun Prakash Jana | 1fb1ab55a7 | |
Martin Roa Villescas | e557bd2ed9 | |
Arun Prakash Jana | defc1965ee | |
Arun Prakash Jana | 32ec37a796 | |
Arun Prakash Jana | f4ff4b0793 | |
Arun Prakash Jana | a58c65a51a | |
Arun Prakash Jana | e2febc986b | |
Jan Meischner | 474ad74f25 | |
Jason | dacf7b0811 | |
Arun Prakash Jana | f17911e189 | |
Arun Prakash Jana | a02ff64e9c | |
Arun Prakash Jana | 387bd048e7 | |
Arun Prakash Jana | 890425c08c | |
Arun Prakash Jana | 1d8a14c6b4 | |
lvgx | 53bbcbc223 | |
Arun Prakash Jana | d3e20e9015 | |
Arun Prakash Jana | 6fa4978230 | |
Arun Prakash Jana | 509f069818 | |
Arun Prakash Jana | 709e7bd7dd | |
Arun Prakash Jana | 1faf9f2480 | |
Arun Prakash Jana | 4178aaa98e | |
Arun Prakash Jana | 90cf84186a | |
Arun Prakash Jana | 06651f3f00 | |
KlzXS | 45d96ee60d | |
Arun Prakash Jana | cb9e785145 | |
Arun Prakash Jana | 56b96cbf74 | |
Arun Prakash Jana | b3820df863 | |
Arun Prakash Jana | 37e5e6189a | |
Sijmen J. Mulder | 235eb29614 | |
Sijmen J. Mulder | 3686ef756a | |
Arun Prakash Jana | 306af787ca | |
KlzXS | 6147dc9a85 | |
Arun Prakash Jana | 28bf18adab | |
lvgx | 7a1a4e293e | |
Mario | 9b5b2b544c | |
Arun Prakash Jana | d7e5e420eb | |
akimdi | 6548a0fa7c | |
Arun Prakash Jana | 4b4bf6cca5 | |
Arun Prakash Jana | d9b8b0e821 | |
Arun Prakash Jana | 251a9a2e9c | |
Arun Prakash Jana | 7c802cce60 | |
Arun Prakash Jana | b3076e35d6 | |
Arun Prakash Jana | a1ec2236d8 | |
Arun Prakash Jana | d92cecba6c | |
Mario | 5a565675c0 | |
Ian R | 1f22da2994 | |
Arun Prakash Jana | 2d5952fef7 | |
Arun Prakash Jana | 0f67e1ff7d | |
Arun Prakash Jana | a103f513c3 | |
Arun Prakash Jana | ef0e973134 | |
Doron Behar | 92ff1447c0 | |
Mario | 7b68844a05 | |
Mario | 9130db3e75 | |
Mario | 5a6078967b | |
Arun Prakash Jana | b3e2ffc2e6 | |
Arun Prakash Jana | 05b1db059e | |
Arun Prakash Jana | 796334354e | |
Arun Prakash Jana | b481b23280 | |
Mario | eeb802280d | |
Mario | c203ae7fa8 | |
Arun Prakash Jana | aea8f737f6 | |
Mario | a47d190654 | |
Arun Prakash Jana | c5f0a25e7e | |
Arun Prakash Jana | d19d8d5f02 | |
Arun Prakash Jana | b62adec72c | |
Arun Prakash Jana | fdfbac0386 | |
lvgx | 58411446b7 | |
Arun Prakash Jana | 65cf067dc4 | |
ncoder-1 | 4d4f72460d | |
Arun Prakash Jana | 056ef8b23d | |
KlzXS | 1f3ce3ae94 | |
Arun Prakash Jana | 10a43a4fbb | |
lvgx | 2acc7bd324 | |
KlzXS | 7b606e0e29 | |
Arun Prakash Jana | 56eea7e195 | |
Todd Yamakawa | 995fa1ceb6 | |
Arun Prakash Jana | 58fd92c7ae | |
Arun Prakash Jana | 2fc115bddc | |
Arun Prakash Jana | 709c0d209e | |
Arun Prakash Jana | 63e90c573b | |
Arun Prakash Jana | 1dbbc45c78 | |
Arun Prakash Jana | 61b4416e08 | |
lvgx | 01da467547 | |
Arun Prakash Jana | 5dbb511ede | |
Arun Prakash Jana | 0ebc6db163 | |
Arun Prakash Jana | ca8bc8bf30 | |
Arun Prakash Jana | f6d9a6b34d | |
Arun Prakash Jana | 9fddd416ca | |
Arun Prakash Jana | 16356e9d06 | |
Arun Prakash Jana | 52697e76d5 | |
Sijmen J. Mulder | 68b9185071 | |
Arun Prakash Jana | f5b5cf5fd7 | |
Arun Prakash Jana | 8549121d86 | |
Arun Prakash Jana | 7263a5f89b | |
Arun Prakash Jana | 4a2d978630 | |
Arun Prakash Jana | 984cffecc4 | |
Arun Prakash Jana | 0b3e48ad41 | |
Arun Prakash Jana | 9de3a3c2ec | |
Arun Prakash Jana | 8e9c4ec88b | |
Arun Prakash Jana | 04f9698d86 | |
basbebe | 3feae709ac | |
Arun Prakash Jana | 309ed0ed67 | |
Arun Prakash Jana | 9e09fb53a1 | |
Arun Prakash Jana | e3d90a98ce | |
Arun Prakash Jana | 4d291d0ac2 | |
Arun Prakash Jana | 32ab43a9ff | |
Arun Prakash Jana | c48b8d02a1 | |
lvgx | f4acf23c15 | |
Mischievous Meerkat | e47a04865e | |
lvgx | 41dc17883a | |
Léo Villeveygoux | 75e8bf44be | |
Léo Villeveygoux | 3426d0d0a3 | |
Arun Prakash Jana | 2232772db4 | |
basbebe | 0a318bd411 | |
Arun Prakash Jana | 87bb2d7742 | |
Arun Prakash Jana | 2599564e64 | |
Arun Prakash Jana | dd5a936bf4 | |
lvgx | 135821aa52 | |
lvgx | bbcd89c8d6 | |
SZ Lin (林上智) | b6762e292c | |
Arun Prakash Jana | e688188fa6 | |
Arun Prakash Jana | 713bab21ea | |
Arun Prakash Jana | 9b7b9d80be | |
Arun Prakash Jana | d7fb77861f | |
Arun Prakash Jana | 38829e5610 | |
Arun Prakash Jana | 56886922a6 | |
Arun Prakash Jana | c1f88d00ff | |
Arun Prakash Jana | 3527f68554 | |
lvgx | b1027150ed | |
lvgx | c7af686b4e | |
lvgx | adf381acee | |
Arun Prakash Jana | a4909beb44 | |
Arun Prakash Jana | 9e41c39138 | |
Arun Prakash Jana | c6c1514c6b | |
lvgx | 0c916ae7b0 | |
Arun Prakash Jana | b465bf9427 | |
Arun Prakash Jana | 709b2f229e | |
Arun Prakash Jana | 1b5c3096ca | |
Arun Prakash Jana | cafcf1c485 | |
Arun Prakash Jana | 54d9a6e4f9 | |
lvgx | a17ef6699d | |
Arun Prakash Jana | 5ea6bc338b | |
Arun Prakash Jana | 74b95eb9bd | |
Arun Prakash Jana | 0f01bd7d3a | |
Arun Prakash Jana | 124666cb38 | |
Arun Prakash Jana | 23770ed049 | |
lvgx | 2200a1c9be | |
Arun Prakash Jana | 770bb47daf | |
Arun Prakash Jana | 38e61fb864 | |
Arun Prakash Jana | dd4173551f | |
Arun Prakash Jana | 24d2bc9d3a | |
Arun Prakash Jana | f46ec76e99 | |
Arun Prakash Jana | 5f3faf613a | |
Arun Prakash Jana | 861d44f934 | |
Arun Prakash Jana | cfd4a66596 | |
Arun Prakash Jana | 14beb0746f | |
Arun Prakash Jana | 609561494f | |
Arun Prakash Jana | f0535dbd76 | |
Arun Prakash Jana | 0b0166816a | |
Arun Prakash Jana | 7718936737 | |
Arun Prakash Jana | 1f51417c63 | |
Arun Prakash Jana | 151bbf000d | |
Arun Prakash Jana | d71379e5b6 | |
Arun Prakash Jana | db3a46a197 | |
lvgx | fcab64263e | |
lvgx | 11c9648774 | |
Arun Prakash Jana | 2a5f8433b8 | |
Arun Prakash Jana | 900b37c56c | |
Arun Prakash Jana | ab9f560fa8 | |
Arun Prakash Jana | ce06bf15d6 | |
Arun Prakash Jana | 4832fc5fe1 | |
Todd Yamakawa | c8ecf06c51 | |
Arun Prakash Jana | bf078c0a8a | |
Arun Prakash Jana | 8568cd6770 | |
Arun Prakash Jana | cfbb8f2117 | |
lvgx | f438ddc28c | |
Léo Villeveygoux | 5b34d0dbe7 | |
Arun Prakash Jana | 2ea3ce552a | |
lvgx | ba51b36931 | |
Arun Prakash Jana | c360f5c908 | |
Arun Prakash Jana | 33c4b1e7a2 | |
Arun Prakash Jana | 97df7df297 | |
lvgx | f47700a609 | |
Arun Prakash Jana | 4c18f22587 | |
Arun Prakash Jana | a563c1a553 | |
0xACE | 65da1c1941 | |
0xACE | c9f0e279af | |
Arun Prakash Jana | 6ee257920d | |
Arun Prakash Jana | a950510342 | |
Arun Prakash Jana | 69e132e36d | |
lvgx | 86e579799b | |
Arun Prakash Jana | b5de18c28f | |
Arun Prakash Jana | 625c8d11f4 | |
Arun Prakash Jana | f2fd923573 | |
Arun Prakash Jana | ffc0790fba | |
Arun Prakash Jana | 92f8fe14f2 | |
Arun Prakash Jana | af71d470f5 | |
Arun Prakash Jana | ebb6f153b5 | |
Arun Prakash Jana | 3f60a1931f | |
Arun Prakash Jana | 8b764a5f7c | |
Arun Prakash Jana | eee5057da5 | |
Danh Doan | e8e87f6ba2 | |
Arun Prakash Jana | ff568ea748 | |
Arun Prakash Jana | f5c6f4f90b | |
Rami3L | 45a69f1cbf | |
Arun Prakash Jana | cb202e128b | |
Arun Prakash Jana | d7a53fd518 | |
lvgx | e68d0db949 | |
lvgx | 1a78ad4aff | |
step | 49eecd7684 | |
Arun Prakash Jana | 73e3f2bca0 | |
Arun Prakash Jana | 283a29c48f | |
Arun Prakash Jana | 3ba456c150 | |
Arun Prakash Jana | da91228bba | |
Arun Prakash Jana | f1a9446b99 | |
Arun Prakash Jana | 187750556c | |
Arun Prakash Jana | 35fb89b972 | |
Arun Prakash Jana | eec0e6d18e | |
KlzXS | babf379a74 | |
Arun Prakash Jana | e7147c1f39 | |
Arun Prakash Jana | 33fdbc2216 | |
Arun Prakash Jana | 6689870460 | |
Arun Prakash Jana | 01392d48ad | |
Arun Prakash Jana | 99d21531b4 | |
Arun Prakash Jana | c732de32e4 | |
Arun Prakash Jana | 06fe7d52dd | |
Arun Prakash Jana | f8a243ea91 | |
Arun Prakash Jana | d118c4cc24 | |
Arun Prakash Jana | fffaa74a09 | |
KlzXS | 7b7252dd32 | |
Arun Prakash Jana | bc572df55a | |
Arun Prakash Jana | 752bc67de0 | |
Arun Prakash Jana | b11bdc9361 | |
lvgx | 7dab9d0d86 | |
KlzXS | 00148360e4 | |
Krisan Alifari | d549ae7486 | |
Arun Prakash Jana | 4b5ecbe8fc | |
Arun Prakash Jana | 12df1ab083 | |
Arun Prakash Jana | b40e12ee9f | |
Arun Prakash Jana | 75724f9e3b | |
Arun Prakash Jana | e38c0108ba | |
Arun Prakash Jana | 645f43355e | |
Todd Yamakawa | c63fb28eff | |
Arun Prakash Jana | 58ecc240ed | |
Arun Prakash Jana | e92b523976 | |
lvgx | 7cc46510e3 | |
Arun Prakash Jana | ddaddcaf21 | |
Arun Prakash Jana | 37ebf8054f | |
Arun Prakash Jana | 63c177bb15 | |
Arun Prakash Jana | 135172a1c6 | |
Arun Prakash Jana | 124d66dcbd | |
Arun Prakash Jana | 425c0559a5 | |
Arun Prakash Jana | ac8b56ecc2 | |
Arun Prakash Jana | 588b413832 | |
Arun Prakash Jana | 30a6caf8bc | |
Arun Prakash Jana | e0cdbcb521 | |
Arun Prakash Jana | 1029ff0d5b | |
Arun Prakash Jana | 555492276c | |
Arun Prakash Jana | cf3c55b787 | |
Arun Prakash Jana | e72fa538d7 | |
Katrin Leinweber | e83e505659 | |
lvgx | a6cef2504c | |
Arun Prakash Jana | cd1c458c96 | |
Arun Prakash Jana | a9436cfe7b | |
Arun Prakash Jana | c58434d078 | |
Arun Prakash Jana | 35c3497364 | |
Arun Prakash Jana | 315132b363 | |
Krisan Alifari | aa7f1dabdd | |
Arun Prakash Jana | f54d51c863 | |
Arun Prakash Jana | 806b91b60d | |
Arun Prakash Jana | 2b3214bd58 | |
Arun Prakash Jana | 5e0049b6fa | |
Saagar Jha | 3bab34e962 | |
Arun Prakash Jana | 2115d75ac6 | |
Arun Prakash Jana | 0b66191dd5 | |
Arun Prakash Jana | a8da9979b7 | |
Arun Prakash Jana | 36ae4b8250 | |
Arun Prakash Jana | f93bb79de8 | |
Arun Prakash Jana | b3f8e4e511 | |
Arun Prakash Jana | 707e30a590 | |
Arun Prakash Jana | e5ba4f69bb | |
Arun Prakash Jana | 341b1ccb00 | |
Arun Prakash Jana | 46f17885ce | |
Arun Prakash Jana | cee24984bc | |
Arun Prakash Jana | e1ed4c62c5 | |
Arun Prakash Jana | b060115a19 | |
Arun Prakash Jana | 1195dc86e0 | |
Arun Prakash Jana | 078d05dc7a | |
Arun Prakash Jana | 1014d941b1 | |
lvgx | f14fb9c0f9 | |
Arun Prakash Jana | 6d13fce698 | |
Arun Prakash Jana | 0c966b2178 | |
Arun Prakash Jana | 02c02c520d | |
Arun Prakash Jana | 0e3146ebd2 | |
Arun Prakash Jana | 5bd4a65b91 | |
Arun Prakash Jana | 73daf8be5b | |
Arun Prakash Jana | 38bd3c4900 | |
Nick Waywood | 415a6edd4a | |
Nick Waywood | 553f183919 | |
Arun Prakash Jana | a3f509ffc6 | |
Arun Prakash Jana | ef159b9985 | |
Arun Prakash Jana | f8d2be504a | |
Arun Prakash Jana | 91bd84cd5d | |
lvgx | 6e6d3cba0d | |
Arun Prakash Jana | 47ec055651 | |
Arun Prakash Jana | c01857cddb | |
Arun Prakash Jana | 2d27902ac0 | |
Arun Prakash Jana | eea1b5da7d | |
Arun Prakash Jana | a4243edacc | |
Arun Prakash Jana | 54d2580799 | |
Arun Prakash Jana | 9fea0220c4 | |
Arun Prakash Jana | b8ede9895f | |
Arun Prakash Jana | 8f910fe85a | |
Arun Prakash Jana | 3d9905615d | |
Arun Prakash Jana | 267dc04f6c | |
Arun Prakash Jana | d2e83b2cfe | |
Arun Prakash Jana | 6ea33f1db3 | |
Arun Prakash Jana | e9ff65a7b5 | |
Arun Prakash Jana | 0bfc032e5d | |
Arun Prakash Jana | 446266d4c7 | |
Arun Prakash Jana | df1e17a4c2 | |
Arun Prakash Jana | dc7711271c | |
Arun Prakash Jana | 8f3f64b5a6 | |
Arun Prakash Jana | c3ff380354 | |
Arun Prakash Jana | b87cdcde60 | |
Arun Prakash Jana | 22ccf5e2e6 | |
Arun Prakash Jana | 7e063f49d1 | |
Arun Prakash Jana | 72333dcdd6 | |
Arun Prakash Jana | bf057c1007 | |
Arun Prakash Jana | 68fd0d7dd2 | |
Arun Prakash Jana | dc08354b0f | |
Arun Prakash Jana | 48bee9fafe | |
Arun Prakash Jana | 33f2a2f37b | |
Arun Prakash Jana | 49e36a4707 | |
KlzXS | aab90bf515 | |
Arun Prakash Jana | 5e8f0aec35 | |
Arun Prakash Jana | 41f80f1f60 | |
Arun Prakash Jana | 0c55977465 | |
Arun Prakash Jana | f4786da9bc | |
Arun Prakash Jana | 85379a703b | |
Arun Prakash Jana | fc8c5b46b3 | |
Arun Prakash Jana | 1cf50e738f | |
Arun Prakash Jana | b8a973a91a | |
Arun Prakash Jana | a2c2332fc5 | |
Arun Prakash Jana | ea2de804f8 | |
Arun Prakash Jana | 03e6d7d553 | |
KlzXS | c215c5de80 | |
Arun Prakash Jana | 67994ff4b2 | |
Arun Prakash Jana | 4e58ad318c | |
Arun Prakash Jana | 1e53cd8ea1 | |
lvgx | d4b0ffa75e | |
Arun Prakash Jana | 0ef2b61a17 | |
Arun Prakash Jana | 2d952795a8 | |
Arun Prakash Jana | 02754205a2 | |
Arun Prakash Jana | f527dd1c6a | |
KlzXS | 29fe67b799 | |
Arun Prakash Jana | 233b801131 | |
Arun Prakash Jana | bf89040ace | |
lvgx | c9a17d80be | |
Arun Prakash Jana | 3a9ddbd90f | |
KlzXS | f6ff9ae4aa | |
Arun Prakash Jana | 4cd9adfd9b | |
Arun Prakash Jana | 3dbe08aad6 | |
Arun Prakash Jana | d97d152269 | |
Arun Prakash Jana | 9bfda074bd | |
Arun Prakash Jana | 0cb5ddf3f1 | |
Arun Prakash Jana | 1fbaa61052 | |
Arun Prakash Jana | 020619d2b8 | |
Arun Prakash Jana | 646cd10b57 | |
Arun Prakash Jana | 4aa12a2dfb | |
Arun Prakash Jana | 0941e511e4 | |
Arun Prakash Jana | a54a23eae5 | |
Arun Prakash Jana | 146f24e5de | |
Arun Prakash Jana | 78d0ea50f4 | |
Arun Prakash Jana | 5533e38fbb | |
Arun Prakash Jana | db129c9120 | |
Arun Prakash Jana | f3c4dae1dd | |
Arun Prakash Jana | 1224270104 | |
Arun Prakash Jana | ad9f834b64 | |
lvgx | b2f2b78990 | |
Arun Prakash Jana | 2b11601f89 | |
Arun Prakash Jana | 5228528fac | |
Arun Prakash Jana | b52d17caa2 | |
Arun Prakash Jana | 56eb4cab6e | |
Arun Prakash Jana | 77e3183467 | |
Arun Prakash Jana | a5a3a84bd1 | |
Arun Prakash Jana | edb9fe14e4 | |
Arun Prakash Jana | 0d7d0ca7db | |
Arun Prakash Jana | 5198c62863 | |
Arun Prakash Jana | a1e2ef055e | |
Arun Prakash Jana | 37987d487e | |
Arun Prakash Jana | d1fcc5351e | |
Arun Prakash Jana | 88167511f6 | |
Arun Prakash Jana | 76cf0c65d4 | |
Arun Prakash Jana | fc805dac26 | |
Arun Prakash Jana | 9c100f987c | |
Arun Prakash Jana | c9f9ca32dd | |
Arun Prakash Jana | 993ea99b76 | |
Arun Prakash Jana | 4eae58edd3 | |
Arun Prakash Jana | b5339c2dc5 | |
Arun Prakash Jana | 95356681ff | |
Arun Prakash Jana | 74e77f78fa | |
Arun Prakash Jana | c6cc8a5181 | |
Arun Prakash Jana | 05f3d5fdbe | |
Arun Prakash Jana | f12bf0a2ee | |
Arun Prakash Jana | 987cc9b4b3 | |
Arun Prakash Jana | dd2be32382 | |
Arun Prakash Jana | f0f8008014 | |
Arun Prakash Jana | 7aa72ddd79 | |
Arun Prakash Jana | 07437a897c | |
Arun Prakash Jana | 71bac356d6 | |
Arun Prakash Jana | ae1d656a27 | |
Arun Prakash Jana | a780ab1c80 | |
Arun Prakash Jana | d442346755 | |
Arun Prakash Jana | 78372b203a | |
Arun Prakash Jana | 702e29bbe9 | |
Arun Prakash Jana | e73ec218a9 | |
Arun Prakash Jana | 5f419dc603 | |
Arun Prakash Jana | dd5b419742 | |
Arun Prakash Jana | 04ab3751af | |
Arun Prakash Jana | f2ba23bb3a | |
Arun Prakash Jana | f61323cccd | |
Arun Prakash Jana | d0930d0ccf | |
Arun Prakash Jana | 4a91df950b | |
Arun Prakash Jana | 0f03b41995 | |
Arun Prakash Jana | b816a90256 | |
Arun Prakash Jana | ca257e6016 | |
Arun Prakash Jana | a1b8631d96 | |
Arun Prakash Jana | 9f1b51b004 | |
Arun Prakash Jana | f7f53bbd6b | |
Arun Prakash Jana | f6e814e364 | |
Arun Prakash Jana | c5d122e299 | |
Arun Prakash Jana | 39fffbac56 | |
0xACE | 75f6d5d735 | |
Arun Prakash Jana | 9cf77708a1 | |
Arun Prakash Jana | 1a8f9ee459 | |
Arun Prakash Jana | 7837cc277f | |
Arun Prakash Jana | 6024c51839 | |
Arun Prakash Jana | b0ba197555 | |
Arun Prakash Jana | f2c4890d6e | |
Uffe Jakobsen | 1ed015e988 | |
Arun Prakash Jana | 9b199b3253 | |
Arun Prakash Jana | e664b2d29f | |
Arun Prakash Jana | a0339adf84 | |
Arun Prakash Jana | 928f325a74 | |
Arun Prakash Jana | ed616cf746 | |
Arun Prakash Jana | 4bd742dafb | |
Arun Prakash Jana | 80545534a9 | |
Arun Prakash Jana | 4ffb42c73e | |
Arun Prakash Jana | a8bca5f440 | |
Arun Prakash Jana | dda34f5c73 | |
Arun Prakash Jana | f6e7dbf6f9 | |
Arun Prakash Jana | bc7a81921e | |
Arun Prakash Jana | 3532d6c3ab | |
Arun Prakash Jana | fb2793354b | |
Arun Prakash Jana | e318672904 | |
Arun Prakash Jana | 3d5815c5d1 | |
Arun Prakash Jana | 43fc9890e8 | |
Arun Prakash Jana | bc5234be8d | |
Arun Prakash Jana | 58357912bc | |
Arun Prakash Jana | 13e28fdecc | |
Arun Prakash Jana | 0a48b6b8cc | |
Arun Prakash Jana | ae486e36b8 | |
Arun Prakash Jana | 72668069ed | |
Arun Prakash Jana | 1d60b6a475 | |
Arun Prakash Jana | eaba594a9e | |
Arun Prakash Jana | 6d77b04032 | |
Arun Prakash Jana | 05ae384b2d | |
Arun Prakash Jana | 1614ce172b | |
Arun Prakash Jana | 6faab79ba9 | |
Arun Prakash Jana | 06f6435ebd | |
Arun Prakash Jana | 47a2f93e02 | |
Arun Prakash Jana | 04d9b667ed | |
Arun Prakash Jana | 840b4a01a0 | |
Arun Prakash Jana | da4f585188 | |
Arun Prakash Jana | 897f01c2c3 | |
KlzXS | 2390ac7b74 | |
Maxim Baz | 099a9af289 | |
Arun Prakash Jana | c0f423496e | |
Arun Prakash Jana | 4401dbe092 | |
Arun Prakash Jana | 27943b9efb | |
Arun Prakash Jana | c7e2dc0005 | |
Maxim Baz | 6b093f213f | |
Arun Prakash Jana | 6f48a711d4 | |
Arun Prakash Jana | 6aed714347 | |
Sijmen J. Mulder | 46fc9c983c | |
Arun Prakash Jana | c434d8d4bc | |
Arun Prakash Jana | cb6f30fed4 | |
Arun Prakash Jana | 9cbadc12be | |
Arun Prakash Jana | e3d80da2ad | |
Ethan R | 812368cce6 | |
Arun Prakash Jana | 3fd9e6ace7 | |
Arun Prakash Jana | bc177fd266 | |
Arun Prakash Jana | dbcbaa583c | |
Arun Prakash Jana | a2288594d1 | |
Arun Prakash Jana | 1684d7b24e | |
Arun Prakash Jana | e5ad7d81ff | |
Arun Prakash Jana | 196c09ab9b | |
Arun Prakash Jana | e2d37632ea | |
KlzXS | 27617c0446 | |
Arun Prakash Jana | 827875c3ef | |
Arun Prakash Jana | d67ad84360 | |
Arun Prakash Jana | 50df09b918 | |
Arun Prakash Jana | de4b817998 | |
Arun Prakash Jana | d224016011 | |
Arun Prakash Jana | 60dfb79b8d | |
Arun Prakash Jana | a87be62204 | |
Arun Prakash Jana | 8d6f766e75 | |
Arun Prakash Jana | 8df6602fac | |
Arun Prakash Jana | a6f5f1ebc8 | |
Arun Prakash Jana | abd1df8770 | |
Arun Prakash Jana | 9b45b05746 | |
Arun Prakash Jana | d0f26e7c30 | |
Arun Prakash Jana | 3d98daaf27 | |
Arun Prakash Jana | 0f1e648032 | |
Arun Prakash Jana | 7677cd4417 | |
Arun Prakash Jana | 1c6fd9c7d7 | |
Arun Prakash Jana | 5e7c42c822 | |
Arun Prakash Jana | 4d01aa78ae | |
Arun Prakash Jana | 6c2dc7fc95 | |
Arun Prakash Jana | cfdd745611 | |
Arun Prakash Jana | 9b054d51f4 | |
Arun Prakash Jana | afb7efc860 | |
Siddharth Dushantha | 1dd691d20b | |
Arun Prakash Jana | dd02fb6049 | |
Arun Prakash Jana | 5f18a0892c | |
Arun Prakash Jana | 679374680f | |
Arun Prakash Jana | 64667b377d | |
Arun Prakash Jana | 94a233b808 | |
Arun Prakash Jana | 4f233c161a | |
Arun Prakash Jana | feec63ebb3 | |
Arun Prakash Jana | 681b22d5c7 | |
Arun Prakash Jana | 7086df5c78 | |
Arun Prakash Jana | f9d38d1420 | |
Maxim Baz | 0fd1f142c7 | |
Martin Ziemer | 527e995f1f | |
Maxim Baz | d1b2bb1e76 | |
Arun Prakash Jana | 38de6efd48 | |
Arun Prakash Jana | 22454d6893 | |
Arun Prakash Jana | 3a4dd4c469 |
|
@ -3,55 +3,70 @@ version: 2
|
|||
jobs:
|
||||
compile:
|
||||
docker:
|
||||
- image: ubuntu:18.04
|
||||
- image: ubuntu:22.04
|
||||
working_directory: ~/nnn
|
||||
environment:
|
||||
CI_FORCE_TEST: 1
|
||||
parallelism: 4
|
||||
steps:
|
||||
- run:
|
||||
command: |
|
||||
apt update -qq
|
||||
DEBIAN_FRONTEND="noninteractive" TZ="America/New_York" apt-get -y install tzdata
|
||||
apt install -y --no-install-recommends software-properties-common wget gpg-agent shellcheck
|
||||
apt-add-repository -y ppa:jonathonf/gcc-9.1
|
||||
wget -O - https://apt.llvm.org/llvm-snapshot.gpg.key|apt-key add -
|
||||
apt-add-repository -y "deb http://apt.llvm.org/bionic/ llvm-toolchain-bionic-8 main"
|
||||
apt update -qq
|
||||
apt install -y --no-install-recommends git gcc gcc-8 gcc-9 clang clang-8 clang-tidy-8 make pkg-config libncursesw5-dev libreadline-dev
|
||||
apt install -y --no-install-recommends git make pkg-config libncurses-dev libreadline-dev
|
||||
apt install -y --no-install-recommends gcc-9 gcc-10 gcc-11 gcc-12
|
||||
apt install -y --no-install-recommends clang-11 clang-12 clang-13 clang-14 clang-15 clang-tidy-15
|
||||
- checkout
|
||||
- run:
|
||||
command: |
|
||||
export CFLAGS=-Werror
|
||||
make clean
|
||||
echo
|
||||
echo "########## gcc ##########"
|
||||
CC=gcc make strip
|
||||
ls -l nnn
|
||||
make clean
|
||||
echo
|
||||
echo "########## gcc-8 ##########"
|
||||
CC=gcc-8 make strip
|
||||
ls -l nnn
|
||||
make clean
|
||||
echo
|
||||
echo "########## gcc-9 ##########"
|
||||
CC=gcc-9 make strip
|
||||
ls -l nnn
|
||||
make clean
|
||||
echo
|
||||
echo "########## clang ##########"
|
||||
CC=clang make strip
|
||||
echo "########## gcc-10 ##########"
|
||||
CC=gcc-10 make strip
|
||||
ls -l nnn
|
||||
make clean
|
||||
echo
|
||||
echo "########## clang-8 ##########"
|
||||
CC=clang-8 make strip
|
||||
echo "########## gcc-11 ##########"
|
||||
CC=gcc-11 make strip
|
||||
ls -l nnn
|
||||
make clean
|
||||
echo
|
||||
echo "########## clang-tidy-8 ##########"
|
||||
clang-tidy-8 src/* -- -I/usr/include -I/usr/include/ncursesw
|
||||
echo "########## checllcheck ##########"
|
||||
find plugins/ -type f -not -name "*.md" -exec shellcheck -e SC1090 {} +
|
||||
echo "########## gcc-12 ##########"
|
||||
CC=gcc-12 make strip
|
||||
ls -l nnn
|
||||
make clean
|
||||
echo
|
||||
echo "########## clang-11 ##########"
|
||||
CC=clang-11 make strip
|
||||
ls -l nnn
|
||||
make clean
|
||||
echo
|
||||
echo "########## clang-12 ##########"
|
||||
CC=clang-12 make strip
|
||||
ls -l nnn
|
||||
make clean
|
||||
echo
|
||||
echo "########## clang-13 ##########"
|
||||
CC=clang-13 make strip
|
||||
ls -l nnn
|
||||
make clean
|
||||
echo
|
||||
echo "########## clang-14 ##########"
|
||||
CC=clang-14 make strip
|
||||
ls -l nnn
|
||||
make clean
|
||||
echo
|
||||
echo "########## clang-tidy-15 ##########"
|
||||
clang-tidy-15 src/* -- -I/usr/include -I/usr/include/ncursesw
|
||||
echo "########## shellcheck ##########"
|
||||
find plugins/ -type f ! \( -name "*.md" -o -name "*-mac" \) -exec shellcheck {} +
|
||||
|
||||
package-and-publish:
|
||||
machine: true
|
||||
|
@ -59,32 +74,31 @@ jobs:
|
|||
steps:
|
||||
- checkout
|
||||
- run:
|
||||
name: "package with packagecore"
|
||||
name: "auto-generate packages"
|
||||
command: |
|
||||
# Create dist directory if it doesn't exist
|
||||
mkdir ./dist
|
||||
# Clean up
|
||||
rm -rf ./.git
|
||||
rm -rf ./dist/*
|
||||
# Pack source
|
||||
cd ..
|
||||
tar -czf ${CIRCLE_PROJECT_REPONAME}-${CIRCLE_TAG}.tar.gz ${CIRCLE_PROJECT_REPONAME}
|
||||
cd ${CIRCLE_PROJECT_REPONAME}
|
||||
git archive -o ../${CIRCLE_PROJECT_REPONAME}-${CIRCLE_TAG}.tar.gz --format tar.gz --prefix=${CIRCLE_PROJECT_REPONAME}-${CIRCLE_TAG#v}/ ${CIRCLE_TAG}
|
||||
# Use latest installed python3 from pyenv
|
||||
export PYENV_VERSION="$(pyenv versions | grep -Po '\b3\.\d+\.\d+' | tail -1)"
|
||||
pip install packagecore
|
||||
packagecore -c misc/packagecore/packagecore.yaml -o ./dist/ ${CIRCLE_TAG#v}
|
||||
#pip install packagecore
|
||||
#packagecore -c misc/packagecore/packagecore.yaml -o ./dist/ ${CIRCLE_TAG#v}
|
||||
# Move source pack to dist
|
||||
mv ../${CIRCLE_PROJECT_REPONAME}-${CIRCLE_TAG}.tar.gz dist/
|
||||
mv ../${CIRCLE_PROJECT_REPONAME}-${CIRCLE_TAG}.tar.gz ./dist/
|
||||
|
||||
- run:
|
||||
name: "publish to GitHub"
|
||||
command: |
|
||||
go get github.com/tcnksm/ghr
|
||||
go install github.com/tcnksm/ghr@latest
|
||||
ghr -t ${GITHUB_API_TOKEN} -u ${CIRCLE_PROJECT_USERNAME} -r ${CIRCLE_PROJECT_REPONAME} -c ${CIRCLE_SHA1} -replace ${CIRCLE_TAG} ./dist/
|
||||
|
||||
workflows:
|
||||
version: 2
|
||||
|
||||
test:
|
||||
CircleCI:
|
||||
jobs: &all-tests
|
||||
- compile
|
||||
|
||||
|
|
|
@ -1,3 +1,3 @@
|
|||
# These are supported funding model platforms
|
||||
|
||||
custom: https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&hosted_button_id=RMLTQ76JSXJ4Q
|
||||
github: jarun
|
||||
|
|
|
@ -1,33 +0,0 @@
|
|||
#### BUG REPORTS
|
||||
|
||||
If it looks like a local environment issue, please try to debug yourself. Debugging local setup issues is not our top priority.
|
||||
|
||||
Before opening an issue, please try to reproduce on latest master. The bug you noticed might have already been fixed.
|
||||
|
||||
Useful links:
|
||||
|
||||
- compile `nnn` from source - https://github.com/jarun/nnn#from-source
|
||||
- debugging `nnn` - https://github.com/jarun/nnn/wiki/debugging-nnn
|
||||
|
||||
If the issue can be reproduced on master, log it.
|
||||
|
||||
Please provide the environment details. **If that's missing, the issue will be closed without any cited reason.**
|
||||
|
||||
If we need more information and there is no communication from the bug reporter within 7 days from the date of request, we will close the issue. If you have relevant information, resume discussion any time.
|
||||
|
||||
#### FEATURE REQUESTS
|
||||
|
||||
Please consider contributing the feature back to `nnn` yourself. Feel free to discuss in the ToDo list thread. We are more than happy to help.
|
||||
|
||||
--- PLEASE DELETE THIS LINE AND EVERYTHING ABOVE ---
|
||||
|
||||
#### Environment details (Put `x` in the checkbox along with the information)
|
||||
|
||||
[ ] Operating System:
|
||||
[ ] Desktop Environment:
|
||||
[ ] Terminal Emulator:
|
||||
[ ] Shell:
|
||||
[ ] Custom desktop opener (if applicable):
|
||||
[ ] Issue exists on `nnn` master
|
||||
|
||||
#### Exact steps to reproduce the issue
|
|
@ -0,0 +1,42 @@
|
|||
---
|
||||
name: Bug report
|
||||
about: Create a report to help us improve
|
||||
title: ''
|
||||
labels: bug
|
||||
assignees: ''
|
||||
---
|
||||
|
||||
`nnn` comes with excellent documentation (including a Troubleshooting section). If you have a _How to do x_ question, it may have already been answered. Wiki: https://github.com/jarun/nnn/wiki
|
||||
|
||||
If it looks like a local environment issue, please try to debug yourself. Debugging local setup issues is not our top priority.
|
||||
|
||||
If you are looking for a new feature or program option, ensure you have the correct version with the feature installed. Refer to the release notes to confirm.
|
||||
|
||||
Before opening an issue, please try to reproduce on latest master. The bug you noticed might have already been fixed.
|
||||
|
||||
Useful links:
|
||||
|
||||
- compile `nnn` from source - https://github.com/jarun/nnn/wiki/Usage#from-source
|
||||
- debugging `nnn` - https://github.com/jarun/nnn/wiki/Developer-guides#debugging-nnn
|
||||
|
||||
If the issue can be reproduced on master, log it.
|
||||
|
||||
Please provide the environment details. **If that's missing, the issue will be closed without any cited reason.**
|
||||
|
||||
If we need more information and there is no communication from the bug reporter within 7 days from the date of request, we will close the issue. If you have relevant information, resume discussion any time.
|
||||
|
||||
--- PLEASE DELETE THIS LINE AND EVERYTHING ABOVE ---
|
||||
|
||||
#### Environment details (Put `x` in the checkbox along with the information)
|
||||
|
||||
- [ ] Operating System:
|
||||
- [ ] Desktop Environment:
|
||||
- [ ] Terminal Emulator:
|
||||
- [ ] Shell:
|
||||
- [ ] Custom desktop opener (if applicable):
|
||||
- [ ] Program options used:
|
||||
- [ ] Configuration options set:
|
||||
- [ ] Plugins are installed
|
||||
- [ ] Issue exists on `nnn` master
|
||||
|
||||
#### Exact steps to reproduce the issue
|
|
@ -0,0 +1,4 @@
|
|||
contact_links:
|
||||
- name: Idea, Enhancement, Question, Support
|
||||
url: https://github.com/jarun/nnn/discussions
|
||||
about: If you have a question, need support or want to discuss new ideas then please open a discussion thread.
|
|
@ -0,0 +1,49 @@
|
|||
name: GitHubCI
|
||||
|
||||
on:
|
||||
push:
|
||||
branches: [master]
|
||||
pull_request:
|
||||
branches: [master]
|
||||
|
||||
jobs:
|
||||
macOS-gcc:
|
||||
runs-on: macOS-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- name: Compile with gcc
|
||||
env:
|
||||
CC: gcc
|
||||
run: |
|
||||
export CFLAGS="$CFLAGS -Werror"
|
||||
make clean
|
||||
make
|
||||
make clean
|
||||
macOS-clang:
|
||||
runs-on: macOS-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- name: Compile with clang
|
||||
env:
|
||||
CC: clang
|
||||
run: |
|
||||
# see: https://github.com/actions/setup-python/issues/577
|
||||
brew update || true
|
||||
brew install llvm || true
|
||||
brew unlink python@3.11 && brew link python@3.11
|
||||
export PATH="/usr/local/opt/llvm/bin:$PATH"
|
||||
export PATH="/opt/homebrew/opt/llvm/bin:$PATH"
|
||||
export CFLAGS="$CFLAGS -Werror"
|
||||
make clean
|
||||
make
|
||||
make clean
|
||||
clang-tidy src/* -- -I/usr/include
|
||||
ubuntu-patches:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- name: Compile patches with gcc
|
||||
env:
|
||||
CC: gcc
|
||||
run: |
|
||||
make checkpatches
|
|
@ -0,0 +1,42 @@
|
|||
name: "CodeQL"
|
||||
|
||||
on:
|
||||
push:
|
||||
branches: [ "master" ]
|
||||
pull_request:
|
||||
branches: [ "master" ]
|
||||
schedule:
|
||||
- cron: "11 23 * * 3"
|
||||
|
||||
jobs:
|
||||
analyze:
|
||||
name: Analyze
|
||||
runs-on: ubuntu-latest
|
||||
permissions:
|
||||
actions: read
|
||||
contents: read
|
||||
security-events: write
|
||||
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
language: [ cpp, python ]
|
||||
|
||||
steps:
|
||||
- name: Checkout
|
||||
uses: actions/checkout@v3
|
||||
|
||||
- name: Initialize CodeQL
|
||||
uses: github/codeql-action/init@v2
|
||||
with:
|
||||
languages: ${{ matrix.language }}
|
||||
queries: +security-and-quality
|
||||
|
||||
- name: Autobuild
|
||||
uses: github/codeql-action/autobuild@v2
|
||||
if: ${{ matrix.language == 'cpp' || matrix.language == 'python' }}
|
||||
|
||||
- name: Perform CodeQL Analysis
|
||||
uses: github/codeql-action/analyze@v2
|
||||
with:
|
||||
category: "/language:${{ matrix.language }}"
|
|
@ -0,0 +1,26 @@
|
|||
name: 'Lock threads'
|
||||
|
||||
on:
|
||||
schedule:
|
||||
- cron: '0 0 * * *'
|
||||
workflow_dispatch:
|
||||
|
||||
permissions:
|
||||
issues: write
|
||||
pull-requests: write
|
||||
discussions: write
|
||||
|
||||
concurrency:
|
||||
group: lock-threads
|
||||
|
||||
jobs:
|
||||
lock:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: dessant/lock-threads@v5
|
||||
with:
|
||||
github-token: ${{ github.token }}
|
||||
issue-lock-inactive-days: '30'
|
||||
issue-lock-reason: ''
|
||||
pr-lock-inactive-days: '30'
|
||||
pr-lock-reason: ''
|
|
@ -1,2 +1,5 @@
|
|||
*.o
|
||||
*.dSYM
|
||||
nnn
|
||||
src/icons-generated*.h
|
||||
src/icons-hash-gen
|
||||
|
|
58
.travis.yml
58
.travis.yml
|
@ -1,58 +0,0 @@
|
|||
language: c
|
||||
sudo: required
|
||||
services:
|
||||
- docker
|
||||
env:
|
||||
global:
|
||||
- REPO=nnn
|
||||
|
||||
matrix:
|
||||
include:
|
||||
# Access more recent gcc and clang via a Xenial image
|
||||
#- os: linux
|
||||
# dist: trusty
|
||||
# compiler: gcc
|
||||
#- os: linux
|
||||
# dist: trusty
|
||||
# compiler: clang
|
||||
- os: osx
|
||||
compiler: gcc
|
||||
- os: osx
|
||||
compiler: clang
|
||||
|
||||
install:
|
||||
- if [[ "$TRAVIS_OS_NAME" == "osx" ]]; then if [[ "$CC" == "clang" ]]; then brew update; brew install llvm; export PATH="/usr/local/opt/llvm/bin:$PATH"; fi; fi
|
||||
|
||||
script:
|
||||
- export CFLAGS=-Werror;
|
||||
- make clean; make;
|
||||
- make clean;
|
||||
- if [[ "$TRAVIS_OS_NAME" == "osx" ]]; then if [[ "$CC" == "clang" ]]; then clang-tidy src/* -- -I/usr/include; fi; fi
|
||||
|
||||
before_deploy:
|
||||
- cd ..
|
||||
- rm -rf $REPO/.git
|
||||
- tar -czf $REPO-${TRAVIS_TAG}.tar.gz $REPO
|
||||
- cd $REPO
|
||||
- unset CFLAGS
|
||||
- sudo apt-get update -qy
|
||||
- sudo apt-get install -qy python3 python3-pip
|
||||
- sudo python3 -m pip install --upgrade pip
|
||||
- sudo python3 -m pip install --upgrade packagecore setuptools
|
||||
- packagecore -o dist/ "${TRAVIS_TAG#v}"
|
||||
- mv ../$REPO-${TRAVIS_TAG}.tar.gz dist/
|
||||
|
||||
deploy:
|
||||
provider: releases
|
||||
api-key:
|
||||
secure: bdw73zBeBEZtDZGEyFpAksnpwLHTBaC7VP1pONmnsXv4qmMcynASz0LfE4krEdAsRnvxQvqPZXviy/SZ3bmaLpVQmJIC1uRWIyOBE6K/7ddf+wfLy+1uO9EPd/zDF/D28Xy8QJLDGDZI08BY5Fist4XowyvtdW3GRwwDL7TwyZyigr0fkqLJwYcqCpojsHsjXjhkpGZqB5XRztaJ4kIEVz8du03ZU1l5kA9lI8Pdk9+mntOOt6emlaJl+Wr81QkwA8TvGPlZ1VP/+h9YCtlRy/4OuiU+bg5/Atxjh8M6rsq+WpZ3ZdYbR6x5vP78p9f6TsJa4ymGhhW6MhYrKPwdT4oITzZcOXJl6AEoIvrWHQWLY7K3WaEfRbT+DODnXks0ToFKls7wyWfi/AHI0ejeDD5Na5/XhY0jdVYOVvovoY2n8LBaqRTFJDYKoCbJ1S+6myUvvmFVwiZWcgOv9gVX1aaIl4wh+XuzUtPDJTcJtUOE8Q2MWl0bdYVtEkHVRznPXN5u3odrDaeTD3vo+pEaEpshLoSKhCyyWvslSzN7T98ez3aw3KFXoFhXPEg5MEJWy7u359MaVwJIsOGUDAFhy/Y7h83LjQYnu8cmX2wuVrQIRIlGVB0f10GYZzPffZz98I/T0xv75NzpyRs31/wMxvdXz35c8m/yTup4kAkG/1s=
|
||||
file_glob: true
|
||||
file:
|
||||
- dist/*
|
||||
skip_cleanup: true
|
||||
on:
|
||||
condition:
|
||||
- "$TRAVIS_OS_NAME == linux"
|
||||
- "$CC == gcc"
|
||||
tags: true
|
||||
repo: jarun/nnn
|
561
CHANGELOG
561
CHANGELOG
|
@ -1,3 +1,564 @@
|
|||
nnn v4.9 Elixir
|
||||
2023-08-27
|
||||
|
||||
- config option `NNN_ARCHMNT` to specify archive mounter utility
|
||||
- key <kbd>^y</kbd> to jump to next young file
|
||||
- filter adjustment when opening context from plugin
|
||||
- properly update mode after `chmod`
|
||||
- pre-fill selected file name to create link if sel is preferred over hovered
|
||||
- fix crash when `PWD` is empty
|
||||
- make `quitcd.bash_zsh` POSIX-compliant
|
||||
- `nmount` - support `udiskctl` as default
|
||||
- `preview-tui` - support wezterm split size percentage
|
||||
- `preview-tui` - move to bash for environment manipulation through arrays
|
||||
- `fzopen` - handle empty selection
|
||||
- `finder` - use default path to find
|
||||
- add icons for `djvu` files
|
||||
- support Nerd Fonts v3.0.0 and above (older versions are broken by v3.0.0)
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
nnn v4.8 Spritz
|
||||
2023-04-13
|
||||
|
||||
- show total size (key <kbd>S</kbd>) of non-filtered selection in a directory
|
||||
- fix tilde (~) handling in file name
|
||||
- plugin `.nmv` now respects `-u` flag
|
||||
- env var `$NNN_PREFER_SELECTION` exported to all plugins
|
||||
- support for wezterm in `preview-tui`
|
||||
- create new file or directory (tree) on startup
|
||||
- run command as plugin now supports exported variables
|
||||
- use `"$nnn"` anywhere when running command as plugin
|
||||
- set defaults for some prompts on <kbd>Enter</kbd>
|
||||
- improve archive, rename and create new workflows
|
||||
- optimize link creation
|
||||
- allow overwriting regular files on new empty file creation
|
||||
- add patch for colemak keyboard (existing renamed to colemak-dh)
|
||||
- add correct check for Wayland in clipboard plugins
|
||||
- add quitcd script for nushell
|
||||
- plugin `kdeconnect` - send multiple files
|
||||
- plugin `preview-tui`: add `chafa` as preferred image viewer, multiple fixes
|
||||
- plugin `nmount` - misc. improvements
|
||||
- add icon for jxl files
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
nnn v4.7 Cuba libre
|
||||
2022-11-24
|
||||
|
||||
|
||||
- fix <kbd>^N</kbd> not working sometimes (#1449)
|
||||
- fix file remove confirmation prompt
|
||||
- bring back `atool` as the default archive handler
|
||||
- add option `-B` to use `bsdtar` as the archive utility
|
||||
- find and list mode improvements
|
||||
ntinue even if max paths/data size limit is exceeded
|
||||
eed improvements
|
||||
pport listing maximum 16K paths of 64 MiB of data
|
||||
- key <kbd>J</kbd> to jump to an entry or relative offset from current entry
|
||||
- prefill the hard link creation prompt when there's a single target (#1507)
|
||||
- documented workaround for docker container crash (#1407, #1476)
|
||||
- plugin `imgview`: handle arguments as strings (#1509)
|
||||
- plugin `wallpaper`: support Wayland (#1512)
|
||||
- plugin `upload`: handle selection using `ffsend` (#1523)
|
||||
- add Rust icons (#1502)
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
nnn v4.6 Absinthe
|
||||
2022-07-26
|
||||
|
||||
- icon handling overhaul (#1432, #1436)
|
||||
- better performance, memory usage and reduced binary size
|
||||
- emoji support for supporting distros and terminals (#1346)
|
||||
- open the target directory of symlinked bookmarks (#1353)
|
||||
- enable show hidden when a hidden file is passed as argument
|
||||
- add Colemak-DH layout keybinds to patch framework (#1421)
|
||||
- set `bsdtar` as the default archive utility
|
||||
- support 4 byte unicode keybinds (#1428)
|
||||
- enable directory auto-enter during filter operation (`-A` to disable)
|
||||
- enable filter prompt inside the bookmark/plugin dirs
|
||||
- show volume usage information in help
|
||||
- add new icon colors for mp4 and flac files
|
||||
- use `stat -x` for file details on *BSD and macOS (#1389)
|
||||
- interpret suffix `$nnn` when paging (#1355)
|
||||
- disable key <kbd>e</kbd> (edit file) in explorer mode (#1394)
|
||||
- fix double order chars on filter case match change
|
||||
- `.cbcp`: more verbose message on paste without a selection
|
||||
- plugin `preview-tui`: scale-up kitty previews
|
||||
- plugin `preview-tui`: account for ueberzug offset
|
||||
- plugin `preview-tui`: support `SPLIT_SIZE` for preview pane (#1431)
|
||||
- plugin `autojump`: support z.lua
|
||||
- new Makefile target `shellcheck` to verify plugins
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
nnn v4.5 Cachaça
|
||||
2022-04-26
|
||||
|
||||
- disable filter info if file details (option `-i`) enabled
|
||||
- open previous active context on context quit
|
||||
- switch <kbd>^J</kbd> and <kbd>+</kbd> functionality:
|
||||
- <kbd>+</kbd>: toggle file selection
|
||||
- <kbd>^J</kbd>: toggle auto-jump on file open
|
||||
- allow symlink creation with name `@` to a single file (#1345)
|
||||
- clear selection on successful operation at native prompt with "%j" (#1330)
|
||||
- reverse timestamps of entries modified/created within 5 minutes
|
||||
- avoid using non-portable `xargs` flags on macOS (#1299)
|
||||
- quitcd script for Elvish shell > 0.17.0 (#1344)
|
||||
- plugin `openall` to open selected files together (#1333)
|
||||
- plugin `gitroot` to jump to git root directory from a subtree
|
||||
- plugin `gsconnect` to send the selected files to Android using gsconnect
|
||||
- icon for opus and webp files
|
||||
- `preview-tui` - fix gif conversion and whitespace name
|
||||
- `preview-tui` - add support for windows terminal split
|
||||
- `preview-tui` - djvu file previews
|
||||
- `nuke` - add support for `imv` when named _imv_
|
||||
- `gsconnect` - support connection to multiple devices
|
||||
- export `NNN_INCLUDE_HIDDEN` to plugins (#1308)
|
||||
- respect `NNN_TRASH` in `.nmv` (#1306)
|
||||
- add GNU sed as a dependency with support for env var `SED`
|
||||
- use bold `>` to point at current entry in detail mode
|
||||
- add 2 spaces after icons for better visibility
|
||||
- documentation refresh
|
||||
- make option `O_NOSORT` to load directories unsorted on entry
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
nnn v4.4 Tequila
|
||||
2021-11-23
|
||||
|
||||
- support macOS iterm2 in plugin preview-tui (#1196)
|
||||
- use selection at native command prompt with `%j` and `%J`
|
||||
- docs - https://github.com/jarun/nnn/wiki/concepts#special-variables
|
||||
- scroll strings longer than columns in rename/new prompts (#1213, #279)
|
||||
- batch rename symlink targets in listing mode (#1214)
|
||||
- option for recursive rename in plugin .nmv (#1186)
|
||||
- more frequent checks for cancellation during du (#1236)
|
||||
- picker mode: enable auto-proceed
|
||||
- picker mode: don't pick hovered file on <kbd>Enter</kbd> if selection exists
|
||||
- picker mode: fix issue in plugin `fzopen` when used to pick files
|
||||
- send file to explorer FIFO on double left click instead of opening it
|
||||
- new neovim plugin [nnn.nvim](https://github.com/luukvbaal/nnn.nvim)
|
||||
- nvim-only, featuring explorer mode (`-F` flag)
|
||||
- explorer mode for [nnn.vim](https://github.com/mcchrish/nnn.vim#explorer)
|
||||
- remove option `-w`: always place HW cursor on current entry
|
||||
- accept link name when linking a single target (#1201)
|
||||
- option `-i` to show current file information in info bar
|
||||
- force GNU sed on *BSD and Solaris
|
||||
- add `nsxiv` support to nuke, preview-tabbed and imgview (#1230)
|
||||
- fix preview-tui without `-a` (#1208)
|
||||
- pass `pts` in env var for preview-tui to use in `tput` (#1235)
|
||||
- disable editing file in picker mode (#1183)
|
||||
- save session in picker mode (#1190)
|
||||
- use nerd icons for gitstatus patch (#1220)
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
nnn v4.3 Martini
|
||||
2021-09-29
|
||||
|
||||
- cool ASCII art logo in the help screen
|
||||
- add `bookmarks` directory for flexible symlinked bookmarks
|
||||
- new key <kbd>B</kbd> to add a symlinked bookmark for current dir
|
||||
- special variables `$dN`, `$fN` available for plugins/prompt/shell to access
|
||||
dir/hovered file in each context
|
||||
- config `NNN_ORDER` to set directory-specific ordering
|
||||
- show/hide hidden files as per context state in plugin based batch rename
|
||||
- retain search filter history for plugin `finder`
|
||||
- sync multiple instances of `nnn` after operation on selection
|
||||
- signal CWD change to terminal via OSC-7 (#1147)
|
||||
- save complete per-context filter when saving sessions
|
||||
- disable symlink resolution for paths in `NNN_BMS` and arg `PATH`
|
||||
- do not end selection mode on running plugins/prompt/shell
|
||||
- plugin `bookmarks` replaced by symlinked bookmarks support
|
||||
- list open locations in active contexts in help page
|
||||
- make option `O_MATCHFLTR` to discard filter key if no match
|
||||
- configurable `NNN_TMPFILE` to _cd on quit_
|
||||
- disable auto marking directories (use <kbd>-</kbd>)
|
||||
- picker mode improvements
|
||||
- open tty for input if `STDIN` is non-tty
|
||||
- truncate output file before writing
|
||||
- do not double select a file on <kbd>Enter</kbd>
|
||||
- legacy macOS (< 10.12.0) support
|
||||
- no redraw during du calculation, show processed dir name
|
||||
- plugin `xdgdefault`: add dmenu support
|
||||
- user patch `restorepreview`: close/restore `preview-tui` for internal edits
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
nnn v4.2 Mojito
|
||||
2021-07-21
|
||||
|
||||
- `NNN_PLUG` indicator symbol interpretation has **changed**:
|
||||
- `!` - _run-cmd-as-plugin_ (earlier `_`)
|
||||
- `&` - _run-gui-cmd-as-plugin_ (earlier `|`)
|
||||
- `|` (new) - page noninteractive _run-cmd-as-plugin_ output
|
||||
- persistent selection markers (#1086)
|
||||
- option _extract to..._ for archives
|
||||
- mount remote and mount/extract archive to a smart context
|
||||
- confirm file trashing to avoid accidental press of <kbd>x</kbd> (#1101)
|
||||
- insert the last command executed at prompt on <kbd>Up</kbd> or <kbd>Down</kbd>
|
||||
- insert the current file name at empty prompt on <kbd>TAB</kbd>
|
||||
- handle redraw issue on missed `KEY_RESIZE` (#1067)
|
||||
- add force-tty capability to spawn and set pagers to it (#1064)
|
||||
- clear selection mode on deselecting last selected file (#1098)
|
||||
- remove selected hovered entry from selection on deletion
|
||||
- disable filtering in empty directories
|
||||
- ignore last pressed filter character when no matches
|
||||
- fix broken screen on resize while paging (#1072)
|
||||
- fix archive not hovered on creation
|
||||
- remove libgit2 dependency in `gitstatus` patch (#1095)
|
||||
- add `-G` flag for `gitstatus` patch
|
||||
- option `-X` for explorer (persistent picker) mode
|
||||
- option `-F` decommissioned in favour of config `NNN_HELP`
|
||||
- `-F` redefined to multiplex `NNN_FIFO` to preview or explore
|
||||
- support paging noninterative _run-cmd-as-plugin_ output
|
||||
- `nuke` - add option to execute binaries (#1111)
|
||||
- plugin `fzopen` - call `open` on macOS, add option to use `nuke`
|
||||
- plugin `fzcd` will not modify selection
|
||||
- plugin `suedit` - preserve environment
|
||||
- several `preview-tui` fixes
|
||||
- plugin `wall` renamed to `wallpaper`
|
||||
- remove plugin `fzz` - merged into plugin `autojump`
|
||||
- remove plugin `upgrade` - packaging is on OBS now
|
||||
- remove plugin `treeview` - needs minor `preview-tui` tweak
|
||||
- remove plugin `picker` - `nnn -p -` does the same
|
||||
- remove plugin `pdfview` - needs simple change in `pdfread`
|
||||
- remove plugin `uidgid` - use program option `-U`
|
||||
- remove plugins `mediainf`, `hexview` - simple one-liners
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
nnn v4.1.1 Sake
|
||||
2021-06-03
|
||||
|
||||
- fix segfault on session save (#1041)
|
||||
- remove redundant `_Atomic` usage
|
||||
- move [`patches`](../tree/master/patches) directory to top-level
|
||||
- fix and cleanup gitstatus patch
|
||||
- plugin `imgview` improvements (#1049)
|
||||
- restore source-code packing on CircleCI
|
||||
- add Makefile target to compile with musl
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
nnn v4.1
|
||||
2021-06-02
|
||||
|
||||
- a patch management model for approved patches
|
||||
- multi-threaded disk usage calculation using pthreads and FTS
|
||||
- dynamic view update when calculating disk usage
|
||||
- <kbd>Bksp</kbd>/<kbd>Del</kbd> at empty filter prompt to refresh dir
|
||||
- Try to create new context with <kbd>Shift-TAB</kbd>, else reverse cycle
|
||||
- <kbd>Alt+Esc</kbd> to quit context from filter prompt
|
||||
- fix zombies left behind after running plugins (#999)
|
||||
- named persistent sessions (mcchrish/nnn.vim#43)
|
||||
- consider nanosecond resolution when sorting by time (#978)
|
||||
- check external selection in `'c'urrent / 's'el` prompt (#976)
|
||||
- show number of files selected in local selection buffer, if any
|
||||
- `nnn` & picker plugin (e.g. `fzopen`) sync (mcchrish/nnn.vim#82)
|
||||
- make batch rename interactive (#971)
|
||||
- cached uid/gid for performance improvement
|
||||
- fixes for `nnn` with `netbsd-curses`, `musl-fts`, `musl` (#998)
|
||||
- script to statically compile `nnn` with `musl gcc` on Ubuntu
|
||||
- restore hovered file when plugin is chosen from plugin dir
|
||||
- support QuickLook on WSL in `preview-tui` (#959)
|
||||
- toggle `preview-tui` with the same _custom_ plugin key
|
||||
- smoother preview toggling in `preview-tui` (#966)
|
||||
- `listen_on` should be set in kitty.conf for `preview-tui` (#970)
|
||||
- minimal `bat` style in `preview-tui`, honors `$BAT_STYLE`
|
||||
- plugin `preview-tui-ext` supersedes `preview-tui` (#1033)
|
||||
- plugin `fzcd` can now fuzzy search multiple directories
|
||||
- plugin `imgview` supersedes `imgthumb` and `vidthumb`
|
||||
- plugin `umounttree`: unmount remote mntpoint from within
|
||||
- plugin `xdgdefault`: set the default app for hovered file type
|
||||
- plugin `fzplug`: fuzzy find, preview and run other plugins
|
||||
- plugin `cmusq`: queue/play music in `cmus`
|
||||
- plugin `mocplay` renamed to `mocq`
|
||||
- plugin `cleanfilename` renamed to `fixname`
|
||||
- go to last dir on <kbd>~</kbd> (HOME) or <kbd>`</kbd> (ROOT) key repeat
|
||||
- ambiguous key <kbd>^Space</kbd> to select/clear range dropped (#998)
|
||||
- user wiki page for [Themes](https://github.com/jarun/nnn/wiki/Themes)
|
||||
- show selection mark (`+`) in reverse bold for improved visibility
|
||||
- reverse block replaces `>` to mark hovered entry in detail mode
|
||||
- make option `O_CKBOARD` removed
|
||||
- make option `O_NOLOC` renamed to `O_NOLC`
|
||||
- ignore `O_NOLC` if `O_ICONS` or `O_NERD` is specified (#1026)
|
||||
- unicode arrow indicators if `O_ICONS` or `O_NERD` is specified
|
||||
- make option `NOX11`: disable notis, sel-clipboard sync, xterm title
|
||||
- retain filter in _nav-to-type_ mode after file open
|
||||
- fix no files picked with `NNN_TMPFILE` exported and <kbd>q</kbd> to quit
|
||||
- disable xterm title setting in picker mode (#974)
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
nnn v4.0 Sushi
|
||||
2021-04-13
|
||||
|
||||
- show xterm title on option `-x`
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
nnn v3.7
|
||||
2021-04-13
|
||||
|
||||
- allow plugins to clear selection (#884, #889, #917)
|
||||
- do not clear selection on hovered file deletion
|
||||
- resurrect `'c'urrent/'s'el` prompt and option `-u` (#889)
|
||||
- show only file name in reverse in detail mode
|
||||
- more file/mime types supported in `preview-tui-ext`
|
||||
- plugin `mtpmount` - (un)mount MTP devices
|
||||
- plugin `cleanfilename` - more shell-friendly file names
|
||||
- plugin `rsynccp` - copy-paste with visual progress
|
||||
- replace `$HOME` by `~` in address bar
|
||||
- show current path in terminal title (#911)
|
||||
- total links and inode number of hardlink in statusbar
|
||||
- fix symlink to text file not opening in CLI editor (#890)
|
||||
- fix symlink size shown as 0B in statusbar (#888)
|
||||
- show symlink target in statusbar (#893)
|
||||
- show correct disk free/total on macOS (#888)
|
||||
- fix directory disk usage showing as 0 on macOS (#941)
|
||||
- fix name col len with `-C` and icons compiled-in (#936)
|
||||
- refactor printing entries in light/detail modes (#934)
|
||||
- make option `O_CKBOARD` for checker board as indicator
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
nnn v3.6 Nina
|
||||
2021-03-16
|
||||
|
||||
- REPL command prompt (<kbd>Esc</kbd> or <kbd>Enter</kbd> to exit)
|
||||
- invert selection with <kbd>A</kbd>
|
||||
- option `-u` removed (always prefer selection to hovered)
|
||||
- visit start dir on <kbd>@</kbd> when start path is a file
|
||||
- exit filter mode and redraw on <kbd>^L</kbd> if no last filter
|
||||
- plugin `fzcd` now selects the chosen file (#876)
|
||||
- `ueberzug` support in plugin `preview-tui`
|
||||
- new plugin `preview-tui-ext` with extra preview support
|
||||
- clear selection after successful plugin invocation
|
||||
- add method to sync subshell `$PWD` in WIki
|
||||
- clear selection on single file deletion (#812)
|
||||
- copy between instances not working (#864)
|
||||
- plugin `togglex` to toggle exe mode of a selection (#813)
|
||||
- fix `memccpy()` buffer overlap fault on macOS (#786)
|
||||
- show `0 selected` msg on cp/mv with empty selection (#855)
|
||||
- fix frozen terminal caused by opener (#858)
|
||||
- migrate macOS CI to GitHub workflows, retire Travis
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
nnn v3.5 Freddie
|
||||
2020-11-17
|
||||
|
||||
- compile-in Alexey Tourbin's QSORT macro
|
||||
- support Nerd Font patched icons [`make O_NERD=1`]
|
||||
- auto-generate static binaries with icons support
|
||||
- audit and adapt all plugins for macOS
|
||||
- enhance plugin `dups` to delete duplicates interactively
|
||||
- plugin `autojump` now supports `jump` and `zoxide`
|
||||
- support `gio trash` to Trash [`export NNN_TRASH=2`] (#740)
|
||||
- quit program on double <kbd>Esc</kbd> in normal mode (#775)
|
||||
- <kbd>^Space</kbd> replaces <kbd>^K</kbd> for range selection/clear selection
|
||||
- show selection symbol (`+`) next to filename in detail mode (#741)
|
||||
- error & quit on <kbd>Q</kbd> if no selection, else pick to stdout
|
||||
- repeat <kbd>^T</kbd> to cycle sort by time, size and clear
|
||||
- option `-U` to show user & group info in status bar
|
||||
- option `-J` to disable auto-proceed on select (#713)
|
||||
- option `-D` to show dirs in context color with `NNN_FCOLORS`
|
||||
- honor option `-C` for context colors
|
||||
- show indicators if more entries above/below listing (#744)
|
||||
- show missing utility name in flash msg (#753)
|
||||
- exit `preview-tabbed` on <kbd>^C</kbd> (#727)
|
||||
- invoke GNU sed (_gsed_) on macOS (#728)
|
||||
- fix HW cursor moves to wrong line (#735)
|
||||
- fix rollover bug with multiline scroll (#743)
|
||||
- fix input stream not listed with `-s`/`-S` (#777)
|
||||
- fix locker not being invoked
|
||||
- make target `upx` for additional binary compression
|
||||
- compress auto-generated static binaries with upx
|
||||
- make variable `O_NOSSN` to compile out sessions
|
||||
- make variable `O_NOUG` to compile out user & group info
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
nnn v3.4 Emilia
|
||||
2020-08-18
|
||||
|
||||
- icons with icon-specific colors (thanks @KlzXS)
|
||||
- enhanced `NNN_COLORS` with xterm 256 colors support
|
||||
- new colorscheme with `NNN_FCOLORS` (file type specific colors)
|
||||
- switch `-C` to force earlier colorscheme (dirs follow context color)
|
||||
- updates for Haiku (thanks @CodeforEvolution)
|
||||
- fix XFS navigation issue (thanks @ucs1)
|
||||
- optimize archive extension matching on file open
|
||||
- show location in context color
|
||||
- support `host[:dir]` format for remote mounts
|
||||
- clear selection after copy
|
||||
- support traversal on file/dir creation
|
||||
- show selection in reverse in status bar
|
||||
- show status bar indicator `H` when hidden files are listed
|
||||
- show and confirm archive command output
|
||||
- support _cd on quit_ in picker mode
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
nnn v3.3
|
||||
2020-07-14
|
||||
|
||||
- subdir `mounts` for remote and archive mounts
|
||||
- remove mount point on successful unmount of remote/archive
|
||||
- show error and prompt user if `cp`/`mv`/`rm` operation fails
|
||||
- support absolute/relative paths in cp/mv as
|
||||
- mark current path automatically on archive/remote mount
|
||||
- mark current path automatically on target file visit in _find and list_ mode
|
||||
- option `-C` to place HW cursor on hovered for screen readers and braille displays
|
||||
- option `-u` to use selection (if available) and skip `current/sel` prompt
|
||||
- key <kbd>Alt+Esc</kbd> to clear filter prompt and redraw
|
||||
- support <kbd>Esc</kbd> to cancel remove operation
|
||||
- `gpge` & `gpgd`: encrypt and decrypt with GPG
|
||||
- `blknew`: create new files and directories in bulk
|
||||
- `preview-tui`
|
||||
- unified to support `tmux`/`kitty`/`xterm`/`$TERMINAL`
|
||||
- auto-determine split orientation based on terminal height and width
|
||||
- provision to use [`scope.sh`](https://github.com/ranger/ranger/blob/master/ranger/data/scope.sh) and [`pistol`](https://github.com/doronbehar/pistol)
|
||||
- various other improvements
|
||||
- `upload`: send to Firefox Send if [`ffsend`](https://github.com/timvisee/ffsend) is found
|
||||
- `hexview`: add [`hx`](https://github.com/krpors/hx) as alternative hex viewer
|
||||
- `nuke` and `imgview`: add [`imv`](https://github.com/eXeC64/imv) as alternative image viewer
|
||||
- add find (with `fd`) and grep (with `rg`) examples in plugins doc
|
||||
- key <kbd>Esc</kbd> or left click to resend hovered file path to `NNN_FIFO`
|
||||
- show `+` instead of `s` in status bar on selection
|
||||
- <kbd>F5</kbd> removed (misfit for toggle hidden), <kbd>^S</kbd> removed (often masked, redundant)
|
||||
- handle abnormal program termination and remove NNN_PIPE and/or NNN_FIFO
|
||||
- clear selection after successful batch rename, link creation
|
||||
- make option `O_CTX8` for 8 contexts (NOT backward compatible with 4 contexts)
|
||||
- fix issue with child window resize (see #656)
|
||||
- fix issue with `NNNLVL` on macOS (see #639)
|
||||
- fix issue with restoring session with du/au enabled
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
nnn v3.2
|
||||
2020-05-26
|
||||
|
||||
- an official logo
|
||||
- previews
|
||||
- config `NNN_FIFO` to write hovered file paths a previewer can read
|
||||
- plugin `preview-tabbed`: [tabbed](https://tools.suckless.org/tabbed)/xembed based file previewer
|
||||
- plugin `preview-tui`: simple TUI file previewer in tmux/xterm
|
||||
- plugin `preview-kitty`: preview using kitty terminal's capabilities
|
||||
- [live preview](https://github.com/jarun/nnn/wiki/Live-previews) configuration example
|
||||
- find & list
|
||||
- send list of files from (cmd run as) plugin to `nnn`
|
||||
- plugin `finder`: find/fd/fzf/grep/ripgrep/fzf (in subtree) and list in `nnn`
|
||||
- <kbd>Right</kbd> or <kbd>l</kbd> on symlink in list dir takes to target file
|
||||
- persistent session option `-S` [for disk usage, run `nnn -T d` (see help)]
|
||||
- hover on the file when a file path is passed as positional argument
|
||||
- go to first file or match with <kbd>'</kbd> (followed by <kbd>'</kbd> or <kbd>char</kbd>)
|
||||
- config `NNN_SEL` to specify custom selection file
|
||||
- config `NNN_LOCKER` to specify locker program
|
||||
- dim file details in detail mode
|
||||
- call `chdir()` on directory change
|
||||
- option `-l`: number of lines to move on mouse scroll
|
||||
- graphical [keybind map](https://github.com/jarun/nnn/wiki/Usage#graphical-map)
|
||||
- let `NNN_COLORS` override `NO_COLOR`
|
||||
- plugins
|
||||
- option `-P`: run plugin by key at start
|
||||
- run plugins with <kbd>Alt+key</kbd>
|
||||
- allow `NNN_PIPE` usage by commands run as plugin
|
||||
- input format to `NNN_PIPE`: `<ctxcode><opcode><data>` (see plugins doc)
|
||||
- set `ctxcode` to `+` for smart context usage (next inactive, else current)
|
||||
- `getplugs` to fetch plugins by installed version of `nnn`
|
||||
- plugin `mimelist`: list files by mime type in subtree
|
||||
- plugin `bookmarks`: named bookmarks using symlinks
|
||||
- plugin `nbak`: backup `nnn` config
|
||||
- `nuke` adds lowdown as alternative markdown viewer
|
||||
- several plugin improvements
|
||||
- fix broken screen on resize (see #520)
|
||||
- fix broken version sort (see #550)
|
||||
- fix list and pipe modes not working together
|
||||
- fix multiple issues with listing files
|
||||
- fix `@` shown in detail mode for symlink to dir
|
||||
- fix listing files directly under `/`
|
||||
- move to `-std=c11`
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
nnn v3.1
|
||||
2020-04-13
|
||||
|
||||
- unlimited bookmarks and plugin keys
|
||||
- status bar text in context color
|
||||
- support config `NO_COLOR` to disable colors
|
||||
- config `NNN_OPTS` to specify binary options to `nnn`
|
||||
- config `NNN_MCLICK` to emulate configurable key
|
||||
- toggle selection on right click
|
||||
- ignore hard links when calculating disk usage
|
||||
- dim (hard/sym) link names (symlink to file has `@`)
|
||||
- more special keys at empty filter prompt in _type-to-nav_
|
||||
- key <kbd>></kbd> to export file list
|
||||
- option `-F` to show fortune in help and settings screen
|
||||
- option `-T` to specify sort order (obsoletes `-v`)
|
||||
- option to clear sort order
|
||||
- key <kbd>T</kbd> to change time type (access/change/mod)
|
||||
- `.nmv` - internal fully-functional batch renamer plugin
|
||||
- make var `O_NOBATCH` to disable native batch renamer
|
||||
- `nuke` & `imgview` - open all images in directory sxiv
|
||||
- `nuke` - open log files in vi
|
||||
- plugin `x2sel` - system clipboard to selection copier
|
||||
- plugin `fzy` - cd using z database
|
||||
- plugin `fzopen` - support `FZF_DEFAULT_COMMAND`
|
||||
- create new context on TAB without prompt
|
||||
- hover and connect by dir name (within config dir)
|
||||
- move to next entry on current file delete
|
||||
- on single file copy/move, select the copied/moved file
|
||||
- option `-f` to use readline history file (off by default)
|
||||
- use `s` in status bar to indicate selection in progress
|
||||
- make var `O_NOMOUSE` to disable mouse support
|
||||
- do not store `NNN_TRASH` and `-Q` in config/session
|
||||
- add sample .desktop file for XDG compatible DEs
|
||||
- rename _nav-as-you-type_ to _type-to-nav_ mode
|
||||
- fix PCRE case-insensitive regex search
|
||||
- fix no error msg when filter length limit exceeded
|
||||
- fix static package generation
|
||||
- fix broken abort message when started in du-mode
|
||||
- fix filter lost on context switch in non _type-to-nav_ mode
|
||||
- fix broken readline prompt
|
||||
- fix long strings treated as action keys in filter prompt
|
||||
- fix `NNNLVL` not reset when spawned shell is exited
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
nnn v3.0
|
||||
2020-02-12
|
||||
|
||||
- take list of files as input and show
|
||||
- option `-e` replaces `NNN_USE_EDITOR`
|
||||
- option `-t` replaces `NNN_IDLE_TIMEOUT`
|
||||
- PCRE support
|
||||
- more readline bindings for native prompts
|
||||
- run GUI app as plugin
|
||||
- attempt lazy unmount when regular unmount fails
|
||||
- fix unmount on macOS: use `umount`
|
||||
- detect `sshfs` and `rclone` to prompt intelligently
|
||||
- auto-proceed on file open (toggle key <kbd>+</kbd>)
|
||||
- quit with error code on <kbd>Q</kbd>
|
||||
- additional key <kbd>F5</kbd> to toggle hidden
|
||||
- key <kbd>e</kbd> to edit in EDITOR (back on multiple user requests)
|
||||
- option to edit list of files in selection is changed to <kbd>E</kbd>
|
||||
- do not end selection on redraw
|
||||
- `nuke`: [`glow`](https://github.com/charmbracelet/glow) as Markdown viewer
|
||||
- `nuke`: refactor, handle some common video types by extension
|
||||
- file name removed from status bar
|
||||
- static Makefile target
|
||||
- generate, upload static package on release
|
||||
- fix crash on entering empty dir, then Down
|
||||
- fix keypresses lost when showing message
|
||||
- fix #227: `nnn` creates xdg-open zombies
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
nnn v2.9
|
||||
2020-01-15
|
||||
|
||||
|
|
2
LICENSE
2
LICENSE
|
@ -2,7 +2,7 @@ BSD 2-Clause License
|
|||
|
||||
Copyright (c) 2014-2016, Lazaros Koromilas <lostd@2f30.org>
|
||||
Copyright (c) 2014-2016, Dimitris Papastamos <sin@2f30.org>
|
||||
Copyright (c) 2016-2020, Arun Prakash Jana <engineerarun@gmail.com>
|
||||
Copyright (c) 2016-2023, Arun Prakash Jana <engineerarun@gmail.com>
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
|
|
303
Makefile
303
Makefile
|
@ -2,6 +2,8 @@ VERSION = $(shell grep -m1 VERSION $(SRC) | cut -f 2 -d'"')
|
|||
|
||||
PREFIX ?= /usr/local
|
||||
MANPREFIX ?= $(PREFIX)/share/man
|
||||
DESKTOPPREFIX ?= $(PREFIX)/share/applications
|
||||
DESKTOPICONPREFIX ?= $(PREFIX)/share/icons/hicolor
|
||||
STRIP ?= strip
|
||||
PKG_CONFIG ?= pkg-config
|
||||
INSTALL ?= install
|
||||
|
@ -9,9 +11,32 @@ CP ?= cp
|
|||
|
||||
CFLAGS_OPTIMIZATION ?= -O3
|
||||
|
||||
O_DEBUG := 0
|
||||
O_DEBUG := 0 # debug binary
|
||||
O_NORL := 0 # no readline support
|
||||
O_NOLOC := 0 # no locale support
|
||||
O_PCRE := 0 # link with PCRE library
|
||||
O_NOLC := 0 # no locale support
|
||||
O_NOMOUSE := 0 # no mouse support
|
||||
O_NOBATCH := 0 # no built-in batch renamer
|
||||
O_NOFIFO := 0 # no FIFO previewer support
|
||||
O_CTX8 := 0 # enable 8 contexts
|
||||
O_ICONS := 0 # support icons-in-terminal
|
||||
O_NERD := 0 # support icons-nerdfont
|
||||
O_EMOJI := 0 # support emoji
|
||||
O_QSORT := 0 # use Alexey Tourbin's QSORT implementation
|
||||
O_BENCH := 0 # benchmark mode (stops at first user input)
|
||||
O_NOSSN := 0 # disable session support
|
||||
O_NOUG := 0 # disable user, group name in status bar
|
||||
O_NOX11 := 0 # disable X11 integration
|
||||
O_MATCHFLTR := 0 # allow filters without matches
|
||||
O_NOSORT := 0 # disable sorting entries on dir load
|
||||
|
||||
# User patches
|
||||
O_COLEMAK := 0 # change key bindings to colemak compatible layout
|
||||
O_GITSTATUS := 0 # add git status to detail view
|
||||
O_NAMEFIRST := 0 # print file name first, add uid and guid to detail view
|
||||
O_RESTOREPREVIEW := 0 # add preview pipe to close and restore preview pane
|
||||
|
||||
T_ICONS := 0 # test if multiple icons options are set and fail
|
||||
|
||||
# convert targets to flags for backwards compatibility
|
||||
ifneq ($(filter debug,$(MAKECMDGOALS)),)
|
||||
|
@ -20,25 +45,110 @@ endif
|
|||
ifneq ($(filter norl,$(MAKECMDGOALS)),)
|
||||
O_NORL := 1
|
||||
endif
|
||||
ifneq ($(filter noloc,$(MAKECMDGOALS)),)
|
||||
ifneq ($(filter nolc,$(MAKECMDGOALS)),)
|
||||
O_NORL := 1
|
||||
O_NOLOC := 1
|
||||
O_NOLC := 1
|
||||
endif
|
||||
|
||||
ifeq ($(O_DEBUG),1)
|
||||
CPPFLAGS += -DDBGMODE
|
||||
CFLAGS += -g
|
||||
LDLIBS += -lrt
|
||||
ifeq ($(strip $(O_DEBUG)),1)
|
||||
CPPFLAGS += -DDEBUG
|
||||
CFLAGS += -g3
|
||||
endif
|
||||
|
||||
ifeq ($(O_NORL),1)
|
||||
ifeq ($(strip $(O_NORL)),1)
|
||||
CPPFLAGS += -DNORL
|
||||
else ifeq ($(strip $(O_STATIC)),1)
|
||||
CPPFLAGS += -DNORL
|
||||
else
|
||||
LDLIBS += -lreadline
|
||||
endif
|
||||
|
||||
ifeq ($(O_NOLOC),1)
|
||||
CPPFLAGS += -DNOLOCALE
|
||||
ifeq ($(strip $(O_PCRE)),1)
|
||||
CPPFLAGS += -DPCRE
|
||||
LDLIBS += -lpcre
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_NOLC)),1)
|
||||
ifeq ($(strip $(O_ICONS)),1)
|
||||
$(info *** Ignoring O_NOLC since O_ICONS is set ***)
|
||||
else ifeq ($(strip $(O_NERD)),1)
|
||||
$(info *** Ignoring O_NOLC since O_NERD is set ***)
|
||||
else ifeq ($(strip $(O_EMOJI)),1)
|
||||
$(info *** Ignoring O_NOLC since O_EMOJI is set ***)
|
||||
else
|
||||
CPPFLAGS += -DNOLC
|
||||
endif
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_NOMOUSE)),1)
|
||||
CPPFLAGS += -DNOMOUSE
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_NOBATCH)),1)
|
||||
CPPFLAGS += -DNOBATCH
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_NOFIFO)),1)
|
||||
CPPFLAGS += -DNOFIFO
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_CTX8)),1)
|
||||
CPPFLAGS += -DCTX8
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_ICONS)),1)
|
||||
ICONS_INCLUDE = icons-generated-icons-in-term.h
|
||||
CPPFLAGS += -DICONS_IN_TERM -DICONS_INCLUDE=\"$(ICONS_INCLUDE)\"
|
||||
ifeq ($(strip $(T_ICONS)),1)
|
||||
$(error Choose only one system for icons (O_ICONS, O_NERD or O_EMOJI))
|
||||
endif
|
||||
T_ICONS := 1
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_NERD)),1)
|
||||
ICONS_INCLUDE = icons-generated-nerd.h
|
||||
CPPFLAGS += -DNERD -DICONS_INCLUDE=\"$(ICONS_INCLUDE)\"
|
||||
ifeq ($(strip $(T_ICONS)),1)
|
||||
$(error Choose only one system for icons (O_ICONS, O_NERD or O_EMOJI))
|
||||
endif
|
||||
T_ICONS := 1
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_EMOJI)),1)
|
||||
ICONS_INCLUDE = icons-generated-emoji.h
|
||||
CPPFLAGS += -DEMOJI -DICONS_INCLUDE=\"$(ICONS_INCLUDE)\"
|
||||
ifeq ($(strip $(T_ICONS)),1)
|
||||
$(error Choose only one system for icons (O_ICONS, O_NERD or O_EMOJI))
|
||||
endif
|
||||
T_ICONS := 1
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_QSORT)),1)
|
||||
CPPFLAGS += -DTOURBIN_QSORT
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_BENCH)),1)
|
||||
CPPFLAGS += -DBENCH
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_NOSSN)),1)
|
||||
CPPFLAGS += -DNOSSN
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_NOUG)),1)
|
||||
CPPFLAGS += -DNOUG
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_NOX11)),1)
|
||||
CPPFLAGS += -DNOX11
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_MATCHFLTR)),1)
|
||||
CPPFLAGS += -DMATCHFLTR
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_NOSORT)),1)
|
||||
CPPFLAGS += -DNOSORT
|
||||
endif
|
||||
|
||||
ifeq ($(shell $(PKG_CONFIG) ncursesw && echo 1),1)
|
||||
|
@ -51,26 +161,90 @@ else
|
|||
LDLIBS_CURSES ?= -lncurses
|
||||
endif
|
||||
|
||||
CFLAGS += -Wall -Wextra
|
||||
CFLAGS += -std=c11 -Wall -Wextra -Wshadow
|
||||
CFLAGS += $(CFLAGS_OPTIMIZATION)
|
||||
CFLAGS += $(CFLAGS_CURSES)
|
||||
|
||||
LDLIBS += $(LDLIBS_CURSES)
|
||||
LDLIBS += $(LDLIBS_CURSES) -lpthread
|
||||
|
||||
# static compilation needs libgpm development package
|
||||
ifeq ($(strip $(O_STATIC)),1)
|
||||
LDFLAGS += -static
|
||||
LDLIBS += -lgpm
|
||||
endif
|
||||
|
||||
DISTFILES = src nnn.1 Makefile README.md LICENSE
|
||||
SRC = src/nnn.c
|
||||
HEADERS = src/nnn.h
|
||||
BIN = nnn
|
||||
DESKTOPFILE = misc/desktop/nnn.desktop
|
||||
LOGOSVG = misc/logo/logo.svg
|
||||
LOGO64X64 = misc/logo/logo-64x64.png
|
||||
|
||||
COLEMAK = patches/colemak
|
||||
GITSTATUS = patches/gitstatus
|
||||
NAMEFIRST = patches/namefirst
|
||||
RESTOREPREVIEW = patches/restorepreview
|
||||
|
||||
# test if we are on Mac OS X and get X.Y.Z OS version with system binary /usr/bin/sw_vers
|
||||
MACOS_VERSION := $(strip $(shell command -v sw_vers >/dev/null && [ "`sw_vers -productName`" = "Mac OS X" ] && sw_vers -productVersion))
|
||||
# if Mac OS X detected, test if its version is below 10.12.0 relying on "sort -c" returning "disorder" message if the input is not sorted
|
||||
ifneq ($(MACOS_VERSION),)
|
||||
MACOS_BELOW_1012 := $(if $(strip $(shell printf '10.12.0\n%s' "$(MACOS_VERSION)" | sort -ct. -k1,1n -k2,2n -k3,3n 2>&1)),1)
|
||||
endif
|
||||
# if Mac OS X version is below 10.12.0, compile in the replacement clock_gettime and define MACOS_BELOW_1012 so that it's included in nnn.c
|
||||
ifneq ($(MACOS_BELOW_1012),)
|
||||
GETTIME_C = misc/macos-legacy/mach_gettime.c
|
||||
GETTIME_H = misc/macos-legacy/mach_gettime.h
|
||||
SRC += $(GETTIME_C)
|
||||
HEADERS += $(GETTIME_H)
|
||||
CPPFLAGS += -DMACOS_BELOW_1012
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_DEBUG)),1)
|
||||
HEADERS += src/dbg.h
|
||||
endif
|
||||
ifeq ($(strip $(O_QSORT)),1)
|
||||
HEADERS += src/qsort.h
|
||||
endif
|
||||
ifeq ($(strip $(O_EMOJI)),1)
|
||||
HEADERS += src/icons.h src/$(ICONS_INCLUDE)
|
||||
endif
|
||||
ifeq ($(strip $(O_NERD)),1)
|
||||
HEADERS += src/icons.h src/$(ICONS_INCLUDE)
|
||||
endif
|
||||
ifeq ($(strip $(O_ICONS)),1)
|
||||
HEADERS += src/icons.h src/$(ICONS_INCLUDE) src/icons-in-terminal.h
|
||||
endif
|
||||
|
||||
all: $(BIN)
|
||||
|
||||
$(BIN): $(SRC) $(HEADERS)
|
||||
$(CC) $(CPPFLAGS) $(CFLAGS) $(LDFLAGS) -o $@ $< $(LDLIBS)
|
||||
$(BIN): $(SRC) $(HEADERS) Makefile
|
||||
@$(MAKE) --silent prepatch
|
||||
$(CC) $(CPPFLAGS) $(CFLAGS) $(LDFLAGS) -o $@ $(GETTIME_C) $< $(LDLIBS)
|
||||
@$(MAKE) --silent postpatch
|
||||
|
||||
# targets for backwards compatibility
|
||||
debug: $(BIN)
|
||||
norl: $(BIN)
|
||||
noloc: $(BIN)
|
||||
nolc: $(BIN)
|
||||
|
||||
src/$(ICONS_INCLUDE): src/icons-hash.c src/icons.h src/icons-in-terminal.h
|
||||
$(CC) $(CPPFLAGS) $(CFLAGS) $(LDFLAGS) -DICONS_GENERATE -o src/icons-hash-gen src/icons-hash.c
|
||||
./src/icons-hash-gen > $@
|
||||
|
||||
install-desktop: $(DESKTOPFILE)
|
||||
$(INSTALL) -m 0755 -d $(DESTDIR)$(DESKTOPPREFIX)
|
||||
$(INSTALL) -m 0644 $(DESKTOPFILE) $(DESTDIR)$(DESKTOPPREFIX)
|
||||
$(INSTALL) -m 0755 -d $(DESTDIR)$(DESKTOPICONPREFIX)/scalable/apps
|
||||
$(INSTALL) -m 0644 $(LOGOSVG) $(DESTDIR)$(DESKTOPICONPREFIX)/scalable/apps/nnn.svg
|
||||
$(INSTALL) -m 0755 -d $(DESTDIR)$(DESKTOPICONPREFIX)/64x64/apps
|
||||
$(INSTALL) -m 0644 $(LOGO64X64) $(DESTDIR)$(DESKTOPICONPREFIX)/64x64/apps/nnn.png
|
||||
|
||||
uninstall-desktop:
|
||||
$(RM) $(DESTDIR)$(DESKTOPPREFIX)/$(DESKTOPFILE)
|
||||
$(RM) $(DESTDIR)$(DESKTOPICONPREFIX)/scalable/apps/nnn.svg
|
||||
$(RM) $(DESTDIR)$(DESKTOPICONPREFIX)/64x64/apps/nnn.png
|
||||
|
||||
install: all
|
||||
$(INSTALL) -m 0755 -d $(DESTDIR)$(PREFIX)/bin
|
||||
|
@ -85,6 +259,32 @@ uninstall:
|
|||
strip: $(BIN)
|
||||
$(STRIP) $^
|
||||
|
||||
upx: $(BIN)
|
||||
$(STRIP) $^
|
||||
upx -qqq $^
|
||||
|
||||
static:
|
||||
# regular static binary
|
||||
make O_STATIC=1 strip
|
||||
mv $(BIN) $(BIN)-static
|
||||
# static binary with icons-in-terminal support
|
||||
make O_STATIC=1 O_ICONS=1 strip
|
||||
mv $(BIN) $(BIN)-icons-static
|
||||
# static binary with patched nerd font support
|
||||
make O_STATIC=1 O_NERD=1 strip
|
||||
mv $(BIN) $(BIN)-nerd-static
|
||||
# static binary with emoji support
|
||||
make O_STATIC=1 O_EMOJI=1 strip
|
||||
mv $(BIN) $(BIN)-emoji-static
|
||||
|
||||
musl:
|
||||
cp misc/musl/musl-static-ubuntu.sh .
|
||||
./musl-static-ubuntu.sh 1
|
||||
rm ./musl-static-ubuntu.sh
|
||||
|
||||
shellcheck:
|
||||
find ./plugins/ -type f -not -name "*.md" -exec shellcheck {} +
|
||||
|
||||
dist:
|
||||
mkdir -p nnn-$(VERSION)
|
||||
$(CP) -r $(DISTFILES) nnn-$(VERSION)
|
||||
|
@ -96,14 +296,81 @@ sign:
|
|||
gpg --detach-sign --yes nnn-$(VERSION).tar.gz
|
||||
rm -f nnn-$(VERSION).tar.gz
|
||||
|
||||
upload-local: sign static musl
|
||||
$(eval ID=$(shell curl -s 'https://api.github.com/repos/jarun/nnn/releases/tags/v$(VERSION)' | jq .id))
|
||||
# upload sign file
|
||||
curl -XPOST 'https://uploads.github.com/repos/jarun/nnn/releases/$(ID)/assets?name=nnn-$(VERSION).tar.gz.sig' \
|
||||
-H 'Authorization: token $(NNN_SIG_UPLOAD_TOKEN)' -H 'Content-Type: application/pgp-signature' \
|
||||
--upload-file nnn-$(VERSION).tar.gz.sig
|
||||
# upx compress all static binaries
|
||||
upx -qqq $(BIN)-static
|
||||
upx -qqq $(BIN)-icons-static
|
||||
upx -qqq $(BIN)-nerd-static
|
||||
upx -qqq $(BIN)-emoji-static
|
||||
# upload static binary
|
||||
tar -zcf $(BIN)-static-$(VERSION).x86_64.tar.gz $(BIN)-static
|
||||
curl -XPOST 'https://uploads.github.com/repos/jarun/nnn/releases/$(ID)/assets?name=$(BIN)-static-$(VERSION).x86_64.tar.gz' \
|
||||
-H 'Authorization: token $(NNN_SIG_UPLOAD_TOKEN)' -H 'Content-Type: application/x-sharedlib' \
|
||||
--upload-file $(BIN)-static-$(VERSION).x86_64.tar.gz
|
||||
# upload icons-in-terminal compiled static binary
|
||||
tar -zcf $(BIN)-icons-static-$(VERSION).x86_64.tar.gz $(BIN)-icons-static
|
||||
curl -XPOST 'https://uploads.github.com/repos/jarun/nnn/releases/$(ID)/assets?name=$(BIN)-icons-static-$(VERSION).x86_64.tar.gz' \
|
||||
-H 'Authorization: token $(NNN_SIG_UPLOAD_TOKEN)' -H 'Content-Type: application/x-sharedlib' \
|
||||
--upload-file $(BIN)-icons-static-$(VERSION).x86_64.tar.gz
|
||||
# upload patched nerd font compiled static binary
|
||||
tar -zcf $(BIN)-nerd-static-$(VERSION).x86_64.tar.gz $(BIN)-nerd-static
|
||||
curl -XPOST 'https://uploads.github.com/repos/jarun/nnn/releases/$(ID)/assets?name=$(BIN)-nerd-static-$(VERSION).x86_64.tar.gz' \
|
||||
-H 'Authorization: token $(NNN_SIG_UPLOAD_TOKEN)' -H 'Content-Type: application/x-sharedlib' \
|
||||
--upload-file $(BIN)-nerd-static-$(VERSION).x86_64.tar.gz
|
||||
# upload emoji compiled static binary
|
||||
tar -zcf $(BIN)-emoji-static-$(VERSION).x86_64.tar.gz $(BIN)-emoji-static
|
||||
curl -XPOST 'https://uploads.github.com/repos/jarun/nnn/releases/$(ID)/assets?name=$(BIN)-emoji-static-$(VERSION).x86_64.tar.gz' \
|
||||
-H 'Authorization: token $(NNN_SIG_UPLOAD_TOKEN)' -H 'Content-Type: application/x-sharedlib' \
|
||||
--upload-file $(BIN)-emoji-static-$(VERSION).x86_64.tar.gz
|
||||
# upload musl static binary
|
||||
tar -zcf $(BIN)-musl-static-$(VERSION).x86_64.tar.gz $(BIN)-musl-static
|
||||
curl -XPOST 'https://uploads.github.com/repos/jarun/nnn/releases/$(ID)/assets?name=$(BIN)-musl-static-$(VERSION).x86_64.tar.gz' \
|
||||
-H 'Authorization: token $(NNN_SIG_UPLOAD_TOKEN)' -H 'Content-Type: application/x-sharedlib' \
|
||||
--upload-file $(BIN)-musl-static-$(VERSION).x86_64.tar.gz
|
||||
|
||||
clean:
|
||||
$(RM) -f $(BIN) nnn-$(VERSION).tar.gz *.sig
|
||||
$(RM) -f $(BIN) nnn-$(VERSION).tar.gz *.sig $(BIN)-static $(BIN)-static-$(VERSION).x86_64.tar.gz $(BIN)-icons-static $(BIN)-icons-static-$(VERSION).x86_64.tar.gz $(BIN)-nerd-static $(BIN)-nerd-static-$(VERSION).x86_64.tar.gz $(BIN)-emoji-static $(BIN)-emoji-static-$(VERSION).x86_64.tar.gz $(BIN)-musl-static $(BIN)-musl-static-$(VERSION).x86_64.tar.gz src/icons-hash-gen src/icons-generated-*.h
|
||||
|
||||
checkpatches:
|
||||
./patches/check-patches.sh
|
||||
|
||||
prepatch:
|
||||
ifeq ($(strip $(O_NAMEFIRST)),1)
|
||||
patch --forward $(PATCH_OPTS) --strip=1 --input=$(NAMEFIRST)/mainline.diff
|
||||
ifeq ($(strip $(O_GITSTATUS)),1)
|
||||
patch --forward $(PATCH_OPTS) --strip=1 --input=$(GITSTATUS)/namefirst.diff
|
||||
endif
|
||||
else ifeq ($(strip $(O_GITSTATUS)),1)
|
||||
patch --forward $(PATCH_OPTS) --strip=1 --input=$(GITSTATUS)/mainline.diff
|
||||
endif
|
||||
ifeq ($(strip $(O_RESTOREPREVIEW)),1)
|
||||
patch --forward $(PATCH_OPTS) --strip=1 --input=$(RESTOREPREVIEW)/mainline.diff
|
||||
endif
|
||||
ifeq ($(strip $(O_COLEMAK)),1)
|
||||
patch --forward $(PATCH_OPTS) --strip=1 --input=$(COLEMAK)/mainline.diff
|
||||
endif
|
||||
|
||||
postpatch:
|
||||
ifeq ($(strip $(O_NAMEFIRST)),1)
|
||||
ifeq ($(strip $(O_GITSTATUS)),1)
|
||||
patch --reverse $(PATCH_OPTS) --strip=1 --input=$(GITSTATUS)/namefirst.diff
|
||||
endif
|
||||
patch --reverse $(PATCH_OPTS) --strip=1 --input=$(NAMEFIRST)/mainline.diff
|
||||
else ifeq ($(strip $(O_GITSTATUS)),1)
|
||||
patch --reverse $(PATCH_OPTS) --strip=1 --input=$(GITSTATUS)/mainline.diff
|
||||
endif
|
||||
ifeq ($(strip $(O_RESTOREPREVIEW)),1)
|
||||
patch --reverse $(PATCH_OPTS) --strip=1 --input=$(RESTOREPREVIEW)/mainline.diff
|
||||
endif
|
||||
ifeq ($(strip $(O_COLEMAK)),1)
|
||||
patch --reverse $(PATCH_OPTS) --strip=1 --input=$(COLEMAK)/mainline.diff
|
||||
endif
|
||||
|
||||
skip: ;
|
||||
|
||||
.PHONY: all install uninstall strip dist sign clean
|
||||
.PHONY: all install uninstall strip static dist sign upload-local clean install-desktop uninstall-desktop
|
||||
|
|
224
README.md
224
README.md
|
@ -1,179 +1,165 @@
|
|||
<h1 align="center">nnn - <i>type less, do more, wayyy faster</i></h1>
|
||||
<h3 align="center"><img src="misc/logo/logo-128x128.png" alt="nnn"><br>nnn - <i>Supercharge your productivity!</i></h3>
|
||||
|
||||
<p align="center">
|
||||
<a href="https://github.com/jarun/nnn/releases/latest"><img src="https://img.shields.io/github/release/jarun/nnn.svg?maxAge=600" alt="Latest release" /></a>
|
||||
<a href="https://repology.org/project/nnn/versions"><img src="https://repology.org/badge/tiny-repos/nnn.svg" alt="Availability"></a>
|
||||
<a href="https://travis-ci.org/jarun/nnn"><img src="https://img.shields.io/travis/jarun/nnn/master.svg?label=travis" alt="Travis Status" /></a>
|
||||
<a href="https://circleci.com/gh/jarun/workflows/nnn"><img src="https://img.shields.io/circleci/project/github/jarun/nnn.svg?label=circleci" alt="CircleCI Status" /></a>
|
||||
<a href="https://en.wikipedia.org/wiki/Privacy-invasive_software"><img src="https://img.shields.io/badge/privacy-✓-crimson" alt="Privacy Awareness" /></a>
|
||||
<a href="https://github.com/jarun/nnn/blob/master/LICENSE"><img src="https://img.shields.io/badge/license-BSD%202--Clause-yellow.svg?maxAge=2592000" alt="License" /></a>
|
||||
<a href="https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&hosted_button_id=RMLTQ76JSXJ4Q"><img src="https://img.shields.io/badge/PayPal-donate-1eb0fc.svg" alt="Donate via PayPal!" /></a>
|
||||
<a href="https://github.com/jarun/nnn/releases/latest"><img src="https://img.shields.io/github/release/jarun/nnn.svg?maxAge=600&label=rel" alt="Latest release" /></a>
|
||||
<a href="https://repology.org/project/nnn/versions"><img src="https://repology.org/badge/tiny-repos/nnn.svg?header=repos" alt="Availability"></a>
|
||||
<a href="https://circleci.com/gh/jarun/workflows/nnn"><img src="https://img.shields.io/circleci/project/github/jarun/nnn.svg?label=circle%20ci" alt="CircleCI Status" /></a>
|
||||
<a href="https://github.com/jarun/nnn/actions"><img src="https://github.com/jarun/nnn/workflows/ci/badge.svg?branch=master" alt="GitHub CI Status" /></a>
|
||||
<a href="https://en.wikipedia.org/wiki/Privacy-invasive_software"><img src="https://img.shields.io/badge/privacy-✓-crimson?maxAge=2592000" alt="Privacy Awareness" /></a>
|
||||
<a href="https://github.com/jarun/nnn/blob/master/LICENSE"><img src="https://img.shields.io/badge/©-BSD%202--Clause-important.svg?maxAge=2592000" alt="License" /></a>
|
||||
</p>
|
||||
|
||||
<p align="center"><a href="https://www.youtube.com/watch?v=U2n5aGqou9E"><img src="https://i.imgur.com/MPWpmos.png" /></a></p>
|
||||
<p align="center"><i>navigate-as-you-type & du (click to see demo video)</i></p>
|
||||
<p align="center"><a href="http://i.imgur.com/kOld6HT.gif"><img src="https://i.imgur.com/NUsSA2u.jpg"></a></p>
|
||||
|
||||
## Introduction
|
||||
<h3 align="center">[<a
|
||||
href="https://github.com/jarun/nnn#features">Features</a>] [<a
|
||||
href="https://github.com/jarun/nnn#quickstart">Quickstart</a>] [<a
|
||||
href="https://github.com/jarun/nnn/tree/master/plugins#nnn-plugins">Plugins</a>] [<a
|
||||
href="https://github.com/jarun/nnn/wiki">Wiki</a>]</h3>
|
||||
|
||||
`nnn` is a full-featured terminal file manager. It's tiny and nearly 0-config with an [incredible performance](https://github.com/jarun/nnn/wiki/Performance).
|
||||
`nnn` (_n³_) is a full-featured terminal file manager. It's tiny, nearly 0-config and [incredibly fast](https://github.com/jarun/nnn/wiki/Performance).
|
||||
|
||||
`nnn` is also a du analyzer, an app launcher, a batch renamer and a file picker. The [plugin repository](https://github.com/jarun/nnn/tree/master/plugins#nnn-plugins) has tons of plugins and documentation to extend the capabilities further. You can _plug_ new functionality _and play_ with a hotkey. There's an independent [(neo)vim plugin](https://github.com/mcchrish/nnn.vim).
|
||||
It is designed to be unobtrusive with smart workflows to match the trains of thought.
|
||||
|
||||
It runs smoothly on the Pi, [Termux](https://www.youtube.com/watch?v=AbaauM7gUJw), Linux, macOS, BSD, Haiku, Cygwin, WSL, across DEs and GUI utilities or a strictly CLI environment.
|
||||
`nnn` can analyze disk usage, batch rename, launch apps and pick files. The plugin repository has tons of plugins to extend the capabilities further e.g. [live previews](https://github.com/jarun/nnn/wiki/Live-previews), (un)mount disks, find & list, file/dir diff, upload files. A [patch framework](https://github.com/jarun/nnn/tree/master/patches) hosts sizable user-submitted patches which are subjective in nature.
|
||||
|
||||
[**Wiki**](https://github.com/jarun/nnn/wiki).
|
||||
Independent (neo)vim plugins - [nnn.vim](https://github.com/mcchrish/nnn.vim), [vim-floaterm nnn wrapper](https://github.com/voldikss/vim-floaterm#nnn) and [nnn.nvim](https://github.com/luukvbaal/nnn.nvim) (neovim exclusive).
|
||||
|
||||
Runs on the Pi, [Termux](https://www.youtube.com/embed/AbaauM7gUJw) (Android), Linux, macOS, BSD, Haiku, Cygwin, WSL, across DEs or a strictly CLI env.
|
||||
|
||||
[_(there's more)_](https://github.com/jarun/nnn/wiki/Basic-use-cases#the_nnn-magic)
|
||||
|
||||
## Features
|
||||
|
||||
- Resource sensitive
|
||||
- Typically needs less than 3.5MB resident memory
|
||||
- Works with 8-bit colors
|
||||
- Disk-IO sensitive (few disk reads and writes)
|
||||
- No FPU usage (all integer maths, even for file size)
|
||||
- Minimizes screen refresh with fast line redraws
|
||||
- Tiny binary (typically less than 100KB)
|
||||
- Portable
|
||||
- Minimal library deps, easily compilable, tiny binary
|
||||
- No config file, minimal config with sensible defaults
|
||||
- Widely available on many packagers
|
||||
- Unicode support
|
||||
- Quality
|
||||
- Privacy-aware (no unconfirmed user data collection)
|
||||
- POSIX-compliant, follows Linux kernel coding style
|
||||
- Highly optimized, static analysis integrated code
|
||||
- Frugal
|
||||
- Typically needs less than 3.5MB resident memory
|
||||
- Works with 8 colors (and xterm 256 colors)
|
||||
- Disk-IO sensitive (few disk reads and writes)
|
||||
- No FPU usage (all integer maths, even for file size)
|
||||
- Minimizes screen refresh with fast line redraws
|
||||
- Tiny binary (typically around 100KB)
|
||||
- 1-column mode for smaller terminals and form factors
|
||||
- Hackable - compile in/out features and dependencies
|
||||
- Portable
|
||||
- Language-agnostic plugins
|
||||
- Static binary available (no need to install)
|
||||
- Minimal library deps, easy to compile
|
||||
- No config file, minimal config with sensible defaults
|
||||
- Plugin to backup configuration
|
||||
- Widely available on many packagers
|
||||
- Touch enabled, handheld-friendly shortcuts
|
||||
- Unicode support
|
||||
- Modes
|
||||
- Light (default), detail
|
||||
- Disk usage analyzer (block/apparent)
|
||||
- File picker, (neo)vim plugin
|
||||
- Navigation
|
||||
- *Navigate-as-you-type* with dir auto-select
|
||||
- Filter with automatic dir entry on unique match
|
||||
- *Type-to-nav* (turbo navigation/always filter) mode
|
||||
- Contexts (_aka_ tabs/workspaces) with custom colors
|
||||
- Sessions, bookmarks with hotkeys; pin and visit a dir
|
||||
- Remote mounts (needs sshfs, rclone)
|
||||
- Familiar shortcuts (arrows, <kbd>~</kbd>, <kbd>-</kbd>, <kbd>@</kbd>), quick reference
|
||||
- CD on quit (*easy* shell integration)
|
||||
- Sessions, bookmarks, mark and visit a dir
|
||||
- Remote mounts (needs `sshfs`, `rclone`)
|
||||
- Familiar shortcuts (arrows, <kbd>~</kbd>, <kbd>-</kbd>, <kbd>@</kbd>), quick look-up
|
||||
- `cd` on quit (*easy* shell integration)
|
||||
- Proceed to next file on file open and selection
|
||||
- Search
|
||||
- Instant filtering with *search-as-you-type*
|
||||
- Regex and substring (default) matches
|
||||
- Regex (POSIX/PCRE) and string (default) filters
|
||||
- Subtree search plugin to open or edit files
|
||||
- Sort
|
||||
- Ordered pure numeric names by default (visit _/proc_)
|
||||
- Ordered pure numeric names by default (visit `/proc`)
|
||||
- Case-insensitive version (_aka_ natural) sort
|
||||
- By file name, modification/access time, size, extension
|
||||
- By name, access/change/mod (default) time, size, extn
|
||||
- Reverse sort
|
||||
- Directory-specific ordering
|
||||
- Mimes
|
||||
- Open with desktop opener or specify a custom app
|
||||
- Create, list, extract, mount (FUSE based) archives
|
||||
- Option to open all text files in EDITOR
|
||||
- Information
|
||||
- Detailed file information
|
||||
- Media information plugin
|
||||
- Preview hovered files in FIFO-based previewer
|
||||
- Open with desktop opener or specify a custom opener
|
||||
- File-specific colors (or minimal _dirs in context color_)
|
||||
- Icons and Emojis support (customize and compile-in)
|
||||
- Plugin for image, video and audio thumbnails
|
||||
- Create, list, extract (to), mount (FUSE based) archives
|
||||
- Option to open all text files in `$EDITOR`
|
||||
- Convenience
|
||||
- Detailed file stats and mime information
|
||||
- Run plugins and custom commands with hotkeys
|
||||
- FreeDesktop compliant trash (needs trash-cli)
|
||||
- FreeDesktop compliant trash utility integration
|
||||
- Cross-dir file/all/range selection
|
||||
- Batch renamer (feature-limited) for selection or dir
|
||||
- Create (with parents), rename, duplicate files and dirs
|
||||
- Create new file or directory (tree) on startup
|
||||
- Batch renamer for selection or dir
|
||||
- List input stream of file paths from stdin or plugin
|
||||
- Copy (as), move (as), delete, archive, link selection
|
||||
- Notification on cp, mv, rm completion
|
||||
- Dir updates, notification on `cp`, `mv`, `rm` completion
|
||||
- Copy file paths to system clipboard on select
|
||||
- Create (with parents), rename, duplicate (anywhere) files and dirs
|
||||
- Launch GUI apps, run commands, spawn a shell, toggle executable
|
||||
- Hovered file set as `$nnn` at prompt and spawned shell
|
||||
- Launch apps, run commands, spawn a shell, toggle exe
|
||||
- Access context paths/files at prompt or spawned shell
|
||||
- Lock terminal after configurable idle timeout
|
||||
- Capture and show output of a program in help screen
|
||||
- Basic support for screen readers and braille displays
|
||||
|
||||
## Quickstart
|
||||
|
||||
1. Install the [utilities you may need](https://github.com/jarun/nnn#utility-dependencies) based on your regular workflows.
|
||||
2. Configure [cd on quit](https://github.com/jarun/nnn/wiki/Basic-use-cases#configure-cd-on-quit).
|
||||
3. Optionally open all text files in `$VISUAL` (else `$EDITOR`, fallback vi): `export NNN_USE_EDITOR=1`.
|
||||
4. For additional functionality [install plugins](https://github.com/jarun/nnn/tree/master/plugins#installing-plugins).
|
||||
5. To copy selected file paths to system clipboard and show notis on cp, mv, rm completion use option `-x`.
|
||||
6. For a strictly CLI environment, see plugin `nuke`. It's a sample opener you can customize.
|
||||
1. [Install](https://github.com/jarun/nnn/wiki/Usage) `nnn` and the dependencies you need.
|
||||
2. The desktop opener is default. Use `-e` to open text files in the terminal. Optionally [open detached](https://github.com/jarun/nnn/wiki/Basic-use-cases#detached-text).
|
||||
3. Configure [`cd` on quit](https://github.com/jarun/nnn/wiki/Basic-use-cases#configure-cd-on-quit).
|
||||
4. [Sync subshell `$PWD`](https://github.com/jarun/nnn/wiki/Basic-use-cases#sync-subshell-pwd) to `nnn`.
|
||||
5. [Install plugins](https://github.com/jarun/nnn/tree/master/plugins#installation).
|
||||
6. Use `-x` to sync selection to clipboard, show notis on `cp`, `mv`, `rm` and set xterm title.
|
||||
7. For a CLI-only environment, set [`NNN_OPENER`](https://github.com/jarun/nnn/wiki/Usage#configuration) to [`nuke`](https://github.com/jarun/nnn/blob/master/plugins/nuke). Use option `-c`.
|
||||
8. Bid `ls` goodbye! `alias ls='nnn -de'` :sunglasses:
|
||||
9. Visit the [Live previews](https://github.com/jarun/nnn/wiki/Live-previews) and [Troubleshooting](https://github.com/jarun/nnn/wiki/Troubleshooting) Wiki pages.
|
||||
|
||||
Don't memorize! Arrows (or <kbd>h</kbd> <kbd>j</kbd> <kbd>k</kbd> <kbd>l</kbd>), <kbd>/</kbd>, <kbd>q</kbd> suffice. <kbd>Tab</kbd> creates, cycles contexts. <kbd>?</kbd> lists shortcuts.
|
||||
Don't memorize! Arrows, <kbd>/</kbd>, <kbd>q</kbd> suffice. <kbd>Tab</kbd> creates and/or cycles contexts. <kbd>?</kbd> lists shortcuts.
|
||||
|
||||
## Installation
|
||||
[![](https://i.imgur.com/TN3xYQz.jpg)](https://www.youtube.com/embed/-knZwdd1ScU)
|
||||
|
||||
#### Library dependencies
|
||||
[![Wiki](https://img.shields.io/badge/RTFM-nnn%20Wiki-important?maxAge=2592000)](https://github.com/jarun/nnn/wiki)
|
||||
|
||||
A curses library with wide char support (e.g. ncursesw), libreadline (optional) and standard libc.
|
||||
## Videos
|
||||
|
||||
#### Utility dependencies
|
||||
|
||||
| Dependency | Installation | Operation |
|
||||
| --- | --- | --- |
|
||||
| xdg-open (Linux), open(1) (macOS), cygstart<br>(Cygwin), open (Haiku) | base | desktop opener |
|
||||
| file, coreutils (cp, mv, rm), xargs | base | file type, copy, move and remove |
|
||||
| tar, (un)zip [atool/bsdtar for more formats] | base | create, list, extract bzip2, (g)zip, tar |
|
||||
| archivemount, fusermount(3) | optional | mount, unmount archives |
|
||||
| sshfs, [rclone](https://rclone.org/), fusermount(3) | optional | mount, unmount remotes |
|
||||
| trash-cli | optional | trash files (default action: rm) |
|
||||
| vlock (Linux), bashlock (macOS), lock(1) (BSD),<br>peaclock (Haiku) | optional | terminal locker (fallback: [cmatrix](https://github.com/abishekvashok/cmatrix)) |
|
||||
| advcpmv (Linux) ([integration](https://github.com/jarun/nnn/wiki/Advanced-use-cases#show-cp-mv-progress)) | optional | copy, move progress |
|
||||
| `$VISUAL` (else `$EDITOR`), `$PAGER`, `$SHELL` | optional | fallback vi, less, sh |
|
||||
|
||||
#### From a package manager
|
||||
|
||||
Install `nnn` from your package manager. If the version available is dated try an alternative installation method.
|
||||
|
||||
<details><summary>Packaging status (expand)</summary>
|
||||
<p>
|
||||
<br>
|
||||
<a href="https://repology.org/project/nnn/versions"><img src="https://repology.org/badge/vertical-allrepos/nnn.svg" alt="Packaging status"></a>
|
||||
</p>
|
||||
Unlisted packagers:
|
||||
<p>
|
||||
<br>
|
||||
● CentOS (<code>yum --enablerepo=epel install nnn</code>)<br>
|
||||
● <a href="https://notabug.org/milislinux/milis/src/master/talimatname/genel/n/nnn/talimat">Milis Linux</a> (<code>mps kur nnn</code>)<br>
|
||||
● <a href="https://www.nutyx.org/en/?type=pkg&branch=rolling&arch=x86_64&searchpkg=nnn">NuTyX</a> (<code>cards install nnn</code>)<br>
|
||||
● <a href="http://codex.sourcemage.org/test/shell-term-fm/nnn/">Source Mage</a> (<code>cast nnn</code>)<br>
|
||||
</p>
|
||||
</details>
|
||||
|
||||
#### Release packages
|
||||
|
||||
Packages for Arch Linux, CentOS, Debian, Fedora and Ubuntu are auto-generated with the [latest stable release](https://github.com/jarun/nnn/releases/latest).
|
||||
|
||||
#### From source
|
||||
|
||||
Download the latest stable release or clone this repository (*risky*), install deps and compile. On Ubuntu 18.04:
|
||||
|
||||
$ sudo apt-get install pkg-config libncursesw5-dev libreadline-dev
|
||||
$ sudo make strip install
|
||||
|
||||
To compile _without_ libreadline:
|
||||
|
||||
$ sudo apt-get install pkg-config libncursesw5-dev
|
||||
$ sudo make O_NORL=1 strip install
|
||||
|
||||
`PREFIX` is supported, in case you want to install to a different location.
|
||||
|
||||
See the [developer guides](https://github.com/jarun/nnn/wiki/Developer-guides) for source verification, compilation notes on the Pi, Cygwin and other tips.
|
||||
|
||||
#### Shell completion
|
||||
|
||||
Completion scripts for Bash, Fish and Zsh are [available](misc/auto-completion). Refer to your shell's manual for installation instructions.
|
||||
- [nnn file manager on Termux (Android)](https://www.youtube.com/embed/AbaauM7gUJw)
|
||||
- [NNN File Manager](https://www.youtube.com/embed/1QXU4XSqXNo)
|
||||
- [This Week in Linux 114 - TuxDigital](https://www.youtube.com/watch?v=5W9ja0DQjSY&t=2059s)
|
||||
- [nnn file manager basics - Linux](https://www.youtube.com/embed/il2Fm-KJJfM)
|
||||
- [I'M GOING TO USE THE NNN FILE BROWSER! 😮](https://www.youtube.com/embed/U2n5aGqou9E)
|
||||
- [NNN: Is This Terminal File Manager As Good As People Say?](https://www.youtube.com/embed/KuJHo-aO_FA)
|
||||
- [nnn - A File Manager (By Uoou, again.)](https://www.youtube.com/embed/cnzuzcCPYsk)
|
||||
|
||||
## Elsewhere
|
||||
|
||||
- [Wikipedia](https://en.wikipedia.org/wiki/Nnn_(file_manager))
|
||||
- [AddictiveTips](https://www.addictivetips.com/ubuntu-linux-tips/navigate-linux-filesystem/)
|
||||
- [ArchWiki](https://wiki.archlinux.org/index.php/Nnn)
|
||||
- [FOSSMint](https://www.fossmint.com/nnn-linux-terminal-file-browser/)
|
||||
- [gHacks Tech News](https://www.ghacks.net/2019/11/01/nnn-is-an-excellent-command-line-based-file-manager-for-linux-macos-and-bsds/)
|
||||
- Hacker News [[1](https://news.ycombinator.com/item?id=18520898)] [[2](https://news.ycombinator.com/item?id=19850656)]
|
||||
- [It's FOSS](https://itsfoss.com/nnn-file-browser-linux/)
|
||||
- LinuxLinks [[1](https://www.linuxlinks.com/nnn-fast-and-flexible-file-manager/)] [[2](https://www.linuxlinks.com/bestconsolefilemanagers/)]
|
||||
- [Linux Format Issue 265; Manage files with nnn](https://linuxformat.com/archives?issue=265)
|
||||
- LinuxLinks [[1](https://www.linuxlinks.com/nnn-fast-and-flexible-file-manager/)] [[2](https://www.linuxlinks.com/bestconsolefilemanagers/)] [[3](https://www.linuxlinks.com/excellent-system-tools-nnn-portable-terminal-file-manager/)]
|
||||
- [Linux Magazine; FOSSPicks](https://www.linux-magazine.com/Issues/2017/205/FOSSPicks/(offset)/15)
|
||||
- [Make Tech Easier](https://www.maketecheasier.com/nnn-file-manager-terminal/)
|
||||
- [Opensource.com](https://opensource.com/article/22/12/linux-file-manager-nnn)
|
||||
- [Open Source For You](https://www.opensourceforu.com/2019/12/nnn-this-feature-rich-terminal-file-manager-will-enhance-your-productivity/)
|
||||
- [PCLinuxOS Magazine Issue June 2021](https://pclosmag.com/html/Issues/202106/page08.html)
|
||||
- [Suckless Rocks](https://suckless.org/rocks/)
|
||||
- [Ubuntu Full Circle Magazine - Issue 135](https://fullcirclemagazine.org/issue-135/)
|
||||
- [Ubuntu Full Circle Magazine Issue 135; Review: nnn](https://fullcirclemagazine.org/issue-135/)
|
||||
- [Using and Administering Linux: Volume 2: Zero to SysAdmin: Advanced Topics](https://books.google.com/books?id=MqjDDwAAQBAJ&pg=PA32)
|
||||
- [Wikipedia](https://en.wikipedia.org/wiki/Nnn_(file_manager))
|
||||
|
||||
## Developers
|
||||
|
||||
- [Arun Prakash Jana](https://github.com/jarun) (Copyright © 2016-2020)
|
||||
- [Arun Prakash Jana](https://github.com/jarun) (Copyright © 2016-2023)
|
||||
- [0xACE](https://github.com/0xACE)
|
||||
- [Anna Arad](https://github.com/annagrram)
|
||||
- [KlzXS](https://github.com/KlzXS)
|
||||
- [Maxim Baz](https://github.com/maximbaz)
|
||||
- [Léo Villeveygoux](https://github.com/leovilok)
|
||||
- [Luuk van Baal](https://github.com/luukvbaal)
|
||||
- [NRK](https://codeberg.org/NRK)
|
||||
- [Sijmen J. Mulder](https://github.com/sjmulder)
|
||||
- and other contributors
|
||||
|
||||
`nnn` is actively developed. Visit the to the [ToDo list](https://github.com/jarun/nnn/issues/386) to contribute or see the features in progress.
|
||||
Visit the [Tracker](https://github.com/jarun/nnn/issues/1546) thread for a list of features in progress and anything up for grabs. Feel free to [discuss](https://github.com/jarun/nnn/discussions) new ideas or enhancement requests.
|
||||
|
|
|
@ -0,0 +1,22 @@
|
|||
# Contributing
|
||||
Contributions to nnn are welcome! There's always an open issue with the current ToDo list, which contains the proposed features for the next release you can get your hands on. Any small changes or ideas should go in there, rather than in a separate issue.
|
||||
|
||||
Before suggesting changes, please read a bit about [the design principles nnn follows](https://github.com/jarun/nnn/wiki/concepts#design), and make sure you aren't breaking any of them.
|
||||
|
||||
Feel free to join the [Discussions](https://github.com/jarun/nnn/discussions). We highly recommended a discussion before raising a PR.
|
||||
|
||||
## Coding standard
|
||||
|
||||
`nnn` follows the Linux kernel coding style closely. The C source code uses TABs and the plugins use 4 spaces for indentation.
|
||||
|
||||
- Code changes should not break the patch framework. Please run `make checkpatches` to ensure.
|
||||
- Run `make shellcheck` if adding/modifying plugins.
|
||||
|
||||
CI runs patch framework sanity test and `shellcheck`. Please watch out for any failures after raising the PR.
|
||||
|
||||
## Resources
|
||||
The [wiki](https://github.com/jarun/nnn/wiki/Developer-guides) has some resources for developers you might be interested in: building, debugging...
|
||||
|
||||
## Communication
|
||||
* [Gitter chat](https://gitter.im/jarun/nnn)
|
||||
* [GitHub team](https://github.com/nnn-devs) (if you plan on contributing regularly, ask for an invitation).
|
|
@ -15,21 +15,33 @@ _nnn ()
|
|||
-a
|
||||
-A
|
||||
-b
|
||||
-B
|
||||
-c
|
||||
-C
|
||||
-d
|
||||
-D
|
||||
-e
|
||||
-E
|
||||
-f
|
||||
-g
|
||||
-H
|
||||
-i
|
||||
-J
|
||||
-K
|
||||
-l
|
||||
-n
|
||||
-o
|
||||
-p
|
||||
-P
|
||||
-Q
|
||||
-r
|
||||
-R
|
||||
-s
|
||||
-S
|
||||
-v
|
||||
-t
|
||||
-T
|
||||
-u
|
||||
-U
|
||||
-V
|
||||
-x
|
||||
-h
|
||||
|
@ -37,11 +49,21 @@ _nnn ()
|
|||
if [[ $prev == -b ]]; then
|
||||
local bookmarks=$(echo $NNN_BMS | awk -F: -v RS=\; '{print $1}')
|
||||
COMPREPLY=( $(compgen -W "$bookmarks" -- "$cur") )
|
||||
elif [[ $prev == -l ]]; then
|
||||
return 1
|
||||
elif [[ $prev == -p ]]; then
|
||||
COMPREPLY=( $(compgen -f -d -- "$cur") )
|
||||
elif [[ $prev == -P ]]; then
|
||||
local plugins=$(echo $NNN_PLUG | awk -F: -v RS=\; '{print $1}')
|
||||
COMPREPLY=( $(compgen -W "$plugins" -- "$cur") )
|
||||
elif [[ $prev == -s ]]; then
|
||||
local sessions_dir=${XDG_CONFIG_HOME:-$HOME/.config}/nnn/sessions
|
||||
COMPREPLY=( $(cd "$sessions_dir" && compgen -f -d -- "$cur") )
|
||||
elif [[ $prev == -t ]]; then
|
||||
return 1
|
||||
elif [[ $prev == -T ]]; then
|
||||
local keys=$(echo "a d e r s t v" | awk -v RS=' ' '{print $0}')
|
||||
COMPREPLY=( $(compgen -W "$keys" -- "$cur") )
|
||||
elif [[ $cur == -* ]]; then
|
||||
COMPREPLY=( $(compgen -W "${opts[*]}" -- "$cur") )
|
||||
else
|
||||
|
|
|
@ -11,24 +11,36 @@ else
|
|||
set sessions_dir $HOME/.config/nnn/sessions
|
||||
end
|
||||
|
||||
complete -c nnn -s a -d 'use access time'
|
||||
complete -c nnn -s A -d 'disable dir auto-select'
|
||||
complete -c nnn -s a -d 'auto-create NNN_FIFO'
|
||||
complete -c nnn -s A -d 'disable dir auto-enter'
|
||||
complete -c nnn -s b -r -d 'bookmark key to open' -x -a '(echo $NNN_BMS | awk -F: -v RS=\; \'{print $1"\t"$2}\')'
|
||||
complete -c nnn -s B -d 'use bsdtar for archives'
|
||||
complete -c nnn -s c -d 'cli-only opener'
|
||||
complete -c nnn -s C -d 'color by context'
|
||||
complete -c nnn -s d -d 'start in detail mode'
|
||||
complete -c nnn -s D -d 'dirs in context color'
|
||||
complete -c nnn -s e -d 'open text files in $VISUAL/$EDITOR/vi'
|
||||
complete -c nnn -s E -d 'use EDITOR for undetached edits'
|
||||
complete -c nnn -s f -d 'use readline history file'
|
||||
complete -c nnn -s g -d 'regex filters'
|
||||
complete -c nnn -s H -d 'show hidden files'
|
||||
complete -c nnn -s K -d 'detect key collision'
|
||||
complete -c nnn -s n -d 'start in navigate-as-you-type mode'
|
||||
complete -c nnn -s i -d 'show current file info'
|
||||
complete -c nnn -s J -d 'no auto-advance on selection'
|
||||
complete -c nnn -s K -d 'detect key collision and exit'
|
||||
complete -c nnn -s l -r -d 'lines to move per scroll'
|
||||
complete -c nnn -s n -d 'start in type-to-nav mode'
|
||||
complete -c nnn -s o -d 'open files only on Enter'
|
||||
complete -c nnn -s p -r -d 'copy selection to file' -a '-\tstdout'
|
||||
complete -c nnn -s P -r -d 'plugin key to run' -x -a '(echo $NNN_PLUG | awk -F: -v RS=\; \'{print $1"\t"$2}\')'
|
||||
complete -c nnn -s Q -d 'disable quit confirmation'
|
||||
complete -c nnn -s r -d 'show cp, mv progress (Linux-only)'
|
||||
complete -c nnn -s R -d 'disable rollover at edges'
|
||||
complete -c nnn -s s -r -d 'load session by name' -x -a '@\t"last session" (ls $sessions_dir)'
|
||||
complete -c nnn -s S -d 'start in disk usage analyzer mode'
|
||||
complete -c nnn -s v -d 'use version compare to sort files'
|
||||
complete -c nnn -s S -d 'persistent session'
|
||||
complete -c nnn -s t -r -d 'timeout in seconds to lock'
|
||||
complete -c nnn -s T -r -d 'a d e r s t v'
|
||||
complete -c nnn -s u -d 'use selection (no prompt)'
|
||||
complete -c nnn -s U -d 'show user and group'
|
||||
complete -c nnn -s V -d 'show program version and exit'
|
||||
complete -c nnn -s x -d 'notis, sel to system clipboard'
|
||||
complete -c nnn -s x -d 'notis, sel to system clipboard, xterm title'
|
||||
complete -c nnn -s h -d 'show program help'
|
||||
|
|
|
@ -9,26 +9,38 @@
|
|||
setopt localoptions noshwordsplit noksharrays
|
||||
local -a args
|
||||
args=(
|
||||
'(-a)-a[use access time]'
|
||||
'(-A)-A[disable dir auto-select]'
|
||||
'(-a)-a[auto-create NNN_FIFO]'
|
||||
'(-A)-A[disable dir auto-enter]'
|
||||
'(-b)-b[bookmark key to open]:key char'
|
||||
'(-B)-B[use bsdtar for archives]'
|
||||
'(-c)-c[cli-only opener]'
|
||||
'(-C)-C[color by context]'
|
||||
'(-d)-d[start in detail mode]'
|
||||
'(-D)-D[dirs in context color]'
|
||||
'(-e)-e[open text files in $VISUAL/$EDITOR/vi]'
|
||||
'(-E)-E[use EDITOR for undetached edits]'
|
||||
'(-f)-f[use readline history file]'
|
||||
'(-g)-g[regex filters]'
|
||||
'(-H)-H[show hidden files]'
|
||||
'(-K)-K[detect key collision]'
|
||||
'(-n)-n[start in navigate-as-you-type mode]'
|
||||
'(-i)-i[show current file info]'
|
||||
'(-J)-J[no auto-advance on selection]'
|
||||
'(-K)-K[detect key collision and exit]'
|
||||
'(-l)-l[lines to move per scroll]:val'
|
||||
'(-n)-n[start in type-to-nav mode]'
|
||||
'(-o)-o[open files only on Enter]'
|
||||
'(-p)-p[copy selection to file]:file name'
|
||||
'(-P)-P[plugin key to run]:key char'
|
||||
'(-Q)-Q[disable quit confirmation]'
|
||||
'(-r)-r[show cp, mv progress (Linux-only)]'
|
||||
'(-R)-R[disable rollover at edges]'
|
||||
'(-s)-s[load session]:session name'
|
||||
'(-S)-S[start in disk usage analyzer mode]'
|
||||
'(-v)-v[use version compare to sort files]'
|
||||
'(-S)-S[persistent session]'
|
||||
'(-t)-t[timeout to lock]:seconds'
|
||||
'(-T)-T[a d e r s t v]:key'
|
||||
'(-u)-u[use selection (no prompt)]'
|
||||
'(-U)-U[show user and group]'
|
||||
'(-V)-V[show program version and exit]'
|
||||
'(-x)-x[notis, sel to system clipboard]'
|
||||
'(-x)-x[notis, sel to system clipboard, xterm title]'
|
||||
'(-h)-h[show program help]'
|
||||
'*:filename:_files'
|
||||
)
|
||||
|
|
|
@ -0,0 +1,10 @@
|
|||
[Desktop Entry]
|
||||
Type=Application
|
||||
Name=nnn
|
||||
Comment=Terminal file manager
|
||||
Exec=nnn
|
||||
Terminal=true
|
||||
Icon=nnn
|
||||
MimeType=inode/directory
|
||||
Categories=System;FileTools;FileManager;ConsoleOnly
|
||||
Keywords=File;Manager;Management;Explorer;Launcher
|
|
@ -9,9 +9,30 @@ CP ?= cp
|
|||
|
||||
CFLAGS_OPTIMIZATION ?= -O3
|
||||
|
||||
O_DEBUG := 0
|
||||
O_DEBUG := 0 # debug binary
|
||||
O_NORL := 0 # no readline support
|
||||
O_NOLOC := 0 # no locale support
|
||||
O_PCRE := 0 # link with PCRE library
|
||||
O_NOLC := 0 # no locale support
|
||||
O_NOMOUSE := 0 # no mouse support
|
||||
O_NOBATCH := 0 # no built-in batch renamer
|
||||
O_NOFIFO := 0 # no FIFO previewer support
|
||||
O_CTX8 := 0 # enable 8 contexts
|
||||
O_ICONS := 0 # support icons-in-terminal
|
||||
O_NERD := 0 # support icons-nerdfont
|
||||
O_QSORT := 0 # use Alexey Tourbin's QSORT implementation
|
||||
O_BENCH := 0 # benchmark mode (stops at first user input)
|
||||
O_NOSSN := 0 # disable session support
|
||||
O_NOUG := 0 # disable user, group name in status bar
|
||||
O_NOX11 := 0 # disable X11 integration
|
||||
O_MATCHFLTR := 0 # allow filters without matches
|
||||
|
||||
# User patches
|
||||
O_GITSTATUS := 0 # add git status to detail view
|
||||
O_NAMEFIRST := 0 # print file name first, add uid and guid to detail view
|
||||
|
||||
ifeq ($(strip $(O_GITSTATUS)),1)
|
||||
LDLIBS += -lgit2
|
||||
endif
|
||||
|
||||
# convert targets to flags for backwards compatibility
|
||||
ifneq ($(filter debug,$(MAKECMDGOALS)),)
|
||||
|
@ -20,25 +41,86 @@ endif
|
|||
ifneq ($(filter norl,$(MAKECMDGOALS)),)
|
||||
O_NORL := 1
|
||||
endif
|
||||
ifneq ($(filter noloc,$(MAKECMDGOALS)),)
|
||||
ifneq ($(filter nolc,$(MAKECMDGOALS)),)
|
||||
O_NORL := 1
|
||||
O_NOLOC := 1
|
||||
O_NOLC := 1
|
||||
endif
|
||||
|
||||
ifeq ($(O_DEBUG),1)
|
||||
CPPFLAGS += -DDBGMODE
|
||||
ifeq ($(strip $(O_DEBUG)),1)
|
||||
CPPFLAGS += -DDEBUG
|
||||
CFLAGS += -g
|
||||
LDLIBS += -lrt
|
||||
endif
|
||||
|
||||
ifeq ($(O_NORL),1)
|
||||
ifeq ($(strip $(O_NORL)),1)
|
||||
CPPFLAGS += -DNORL
|
||||
else ifeq ($(strip $(O_STATIC)),1)
|
||||
CPPFLAGS += -DNORL
|
||||
else
|
||||
LDLIBS += -lreadline
|
||||
endif
|
||||
|
||||
ifeq ($(O_NOLOC),1)
|
||||
CPPFLAGS += -DNOLOCALE
|
||||
ifeq ($(strip $(O_PCRE)),1)
|
||||
CPPFLAGS += -DPCRE
|
||||
LDLIBS += -lpcre
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_NOLC)),1)
|
||||
ifeq ($(strip $(O_ICONS)),1)
|
||||
$(info *** Ignoring O_NOLC since O_ICONS is set ***)
|
||||
else ifeq ($(strip $(O_NERD)),1)
|
||||
$(info *** Ignoring O_NOLC since O_NERD is set ***)
|
||||
else
|
||||
CPPFLAGS += -DNOLC
|
||||
endif
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_NOMOUSE)),1)
|
||||
CPPFLAGS += -DNOMOUSE
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_NOBATCH)),1)
|
||||
CPPFLAGS += -DNOBATCH
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_NOFIFO)),1)
|
||||
CPPFLAGS += -DNOFIFO
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_CTX8)),1)
|
||||
CPPFLAGS += -DCTX8
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_ICONS)),1)
|
||||
CPPFLAGS += -DICONS
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_NERD)),1)
|
||||
CPPFLAGS += -DNERD
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_QSORT)),1)
|
||||
CPPFLAGS += -DTOURBIN_QSORT
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_BENCH)),1)
|
||||
CPPFLAGS += -DBENCH
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_NOSSN)),1)
|
||||
CPPFLAGS += -DNOSSN
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_NOUG)),1)
|
||||
CPPFLAGS += -DNOUG
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_NOX11)),1)
|
||||
CPPFLAGS += -DNOX11
|
||||
endif
|
||||
|
||||
ifeq ($(strip $(O_MATCHFLTR)),1)
|
||||
CPPFLAGS += -DMATCHFLTR
|
||||
endif
|
||||
|
||||
ifeq ($(shell $(PKG_CONFIG) ncursesw && echo 1),1)
|
||||
|
@ -52,16 +134,21 @@ else
|
|||
endif
|
||||
|
||||
ifeq ($(shell uname -s), Haiku)
|
||||
LDLIBS_HAIKU ?= -lstdc++ -lbe
|
||||
LDLIBS_HAIKU ?= -lstdc++ -lgnu -lbe
|
||||
SRC_HAIKU ?= misc/haiku/nm.cpp
|
||||
OBJS_HAIKU ?= misc/haiku/nm.o
|
||||
endif
|
||||
|
||||
CFLAGS += -Wall -Wextra
|
||||
CFLAGS += -std=c11 -Wall -Wextra -Wshadow
|
||||
CFLAGS += $(CFLAGS_OPTIMIZATION)
|
||||
CFLAGS += $(CFLAGS_CURSES)
|
||||
|
||||
LDLIBS += $(LDLIBS_CURSES) $(LDLIBS_HAIKU)
|
||||
LDLIBS += $(LDLIBS_CURSES) -lpthread $(LDLIBS_HAIKU)
|
||||
# static compilation needs libgpm development package
|
||||
ifeq ($(strip $(O_STATIC)),1)
|
||||
LDFLAGS += -static
|
||||
LDLIBS += -lgpm
|
||||
endif
|
||||
|
||||
DISTFILES = src nnn.1 Makefile README.md LICENSE
|
||||
SRC = src/nnn.c
|
||||
|
@ -69,6 +156,9 @@ HEADERS = src/nnn.h
|
|||
BIN = nnn
|
||||
OBJS := nnn.o $(OBJS_HAIKU)
|
||||
|
||||
GITSTATUS = patches/gitstatus
|
||||
NAMEFIRST = patches/namefirst
|
||||
|
||||
all: $(BIN)
|
||||
|
||||
ifeq ($(shell uname -s), Haiku)
|
||||
|
@ -80,12 +170,14 @@ nnn.o: $(SRC) $(HEADERS)
|
|||
$(CC) -c $(CPPFLAGS) $(CFLAGS) -o $@ $<
|
||||
|
||||
$(BIN): $(OBJS)
|
||||
@$(MAKE) --silent prepatch
|
||||
$(CC) $(LDFLAGS) -o $@ $^ $(LDLIBS)
|
||||
@$(MAKE) --silent postpatch
|
||||
|
||||
# targets for backwards compatibility
|
||||
debug: $(BIN)
|
||||
norl: $(BIN)
|
||||
noloc: $(BIN)
|
||||
nolc: $(BIN)
|
||||
|
||||
install: all
|
||||
$(INSTALL) -m 0755 -d $(DESTDIR)$(PREFIX)/bin
|
||||
|
@ -100,6 +192,11 @@ uninstall:
|
|||
strip: $(BIN)
|
||||
$(STRIP) $^
|
||||
|
||||
static:
|
||||
# regular static binary
|
||||
make O_STATIC=1 strip
|
||||
mv $(BIN) $(BIN)-static
|
||||
|
||||
dist:
|
||||
mkdir -p nnn-$(VERSION)
|
||||
$(CP) -r $(DISTFILES) nnn-$(VERSION)
|
||||
|
@ -113,14 +210,41 @@ sign:
|
|||
gpg --detach-sign --yes nnn-$(VERSION).tar.gz
|
||||
rm -f nnn-$(VERSION).tar.gz
|
||||
|
||||
upload-local: sign static
|
||||
$(eval ID=$(shell curl -s 'https://api.github.com/repos/jarun/nnn/releases/tags/v$(VERSION)' | jq .id))
|
||||
# upload sign file
|
||||
curl -XPOST 'https://uploads.github.com/repos/jarun/nnn/releases/$(ID)/assets?name=nnn-$(VERSION).tar.gz.sig' \
|
||||
-H 'Authorization: token $(NNN_SIG_UPLOAD_TOKEN)' -H 'Content-Type: application/pgp-signature' \
|
||||
--upload-file nnn-$(VERSION).tar.gz.sig
|
||||
tar -zcf $(BIN)-static-$(VERSION).x86_64.tar.gz $(BIN)-static
|
||||
# upload static binary
|
||||
curl -XPOST 'https://uploads.github.com/repos/jarun/nnn/releases/$(ID)/assets?name=$(BIN)-static-$(VERSION).x86_64.tar.gz' \
|
||||
-H 'Authorization: token $(NNN_SIG_UPLOAD_TOKEN)' -H 'Content-Type: application/x-sharedlib' \
|
||||
--upload-file $(BIN)-static-$(VERSION).x86_64.tar.gz
|
||||
|
||||
clean:
|
||||
$(RM) -f $(BIN) $(OBJS) nnn-$(VERSION).tar.gz *.sig
|
||||
$(RM) -f $(BIN) nnn-$(VERSION).tar.gz *.sig $(BIN)-static $(BIN)-static-$(VERSION).x86_64.tar.gz
|
||||
|
||||
prepatch:
|
||||
ifeq ($(strip $(O_NAMEFIRST)),1)
|
||||
patch --forward --strip=1 --input=$(NAMEFIRST)/mainline.diff
|
||||
ifeq ($(strip $(O_GITSTATUS)),1)
|
||||
patch --forward --strip=1 --input=$(GITSTATUS)/namefirst.diff
|
||||
endif
|
||||
else ifeq ($(strip $(O_GITSTATUS)),1)
|
||||
patch --forward --strip=1 --input=$(GITSTATUS)/mainline.diff
|
||||
endif
|
||||
|
||||
postpatch:
|
||||
ifeq ($(strip $(O_NAMEFIRST)),1)
|
||||
ifeq ($(strip $(O_GITSTATUS)),1)
|
||||
patch --reverse --strip=1 --input=$(GITSTATUS)/namefirst.diff
|
||||
endif
|
||||
patch --reverse --strip=1 --input=$(NAMEFIRST)/mainline.diff
|
||||
else ifeq ($(strip $(O_GITSTATUS)),1)
|
||||
patch --reverse --strip=1 --input=$(GITSTATUS)/mainline.diff
|
||||
endif
|
||||
|
||||
skip: ;
|
||||
|
||||
.PHONY: all install uninstall strip dist sign clean
|
||||
.PHONY: all install uninstall strip static dist sign upload-local clean
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
SUMMARY="The missing terminal file manager for X"
|
||||
SUMMARY="A blazing-fast lightweight terminal file manager"
|
||||
DESCRIPTION="nnn is a full-featured terminal file manager. It's tiny and \
|
||||
nearly 0-config with an incredible performance.
|
||||
|
||||
|
@ -8,16 +8,16 @@ capabilities further. You can plug new functionality and play with a \
|
|||
custom keybind instantly. There's an independent (neo)vim plugin.
|
||||
|
||||
It runs smoothly on the Raspberry Pi, Termux on Android, Linux, macOS, BSD, \
|
||||
Cygwin, WSL and works seamlessly with DEs and GUI utilities.
|
||||
Cygwin, WSL, Haiku and works seamlessly with DEs and GUI utilities.
|
||||
|
||||
Visit the Wiki for concepts, program usage, how-tos and troubleshooting."
|
||||
HOMEPAGE="https://github.com/jarun/nnn"
|
||||
COPYRIGHT="2016-2020 Arun Prakash Jana"
|
||||
COPYRIGHT="2016-2023 Arun Prakash Jana"
|
||||
LICENSE="BSD (2-clause)"
|
||||
REVISION="1"
|
||||
SOURCE_URI="git://github.com/jarun/nnn.git"
|
||||
|
||||
ARCHITECTURES="x86_64"
|
||||
ARCHITECTURES="!x86_gcc2 x86_64"
|
||||
SECONDARY_ARCHITECTURES="x86"
|
||||
|
||||
PROVIDES="
|
||||
|
@ -53,4 +53,6 @@ BUILD()
|
|||
INSTALL()
|
||||
{
|
||||
make -f misc/haiku/Makefile install PREFIX=$prefix
|
||||
|
||||
addResourcesToBinaries misc/haiku/nnn.rdef $prefix/bin/nnn
|
||||
}
|
||||
|
|
|
@ -0,0 +1,140 @@
|
|||
|
||||
// How to apply this resource definition file manually (Haiku only):
|
||||
// First, make sure that nnn is compiled.
|
||||
// Next, run "rc nnn.rdef -o nnn.rsrc" to compile this resource file.
|
||||
// Then, run "xres -o nnn nnn.rsrc" to apply the resource file to nnn.
|
||||
// Finally, run "mimeset -f nnn" to refresh Haiku's MIME database.
|
||||
|
||||
resource app_signature "application/x-vnd.Jarun-nnn";
|
||||
|
||||
resource app_version {
|
||||
major = 4,
|
||||
middle = 9,
|
||||
minor = 0,
|
||||
|
||||
variety = B_APPV_DEVELOPMENT,
|
||||
internal = 0,
|
||||
|
||||
short_info = "nnn",
|
||||
long_info = "A blazing-fast lightweight terminal file manager"
|
||||
};
|
||||
|
||||
resource app_flags B_MULTIPLE_LAUNCH | B_BACKGROUND_APP | B_ARGV_ONLY;
|
||||
|
||||
resource file_types message {
|
||||
"types" = "application/x-vnd.Be-directory"
|
||||
};
|
||||
|
||||
resource vector_icon {
|
||||
$"6E6369660805FF032E343602011202B8E0C339BAC3B985CFB8B7E549F5FF4994"
|
||||
$"000000FFFF0000020112023745BA3659FABA87063B846942D03049EBF80000FF"
|
||||
$"FF0000020112033BE54D39FE49B857E23A493A4A91FF489000000000AF0000FF"
|
||||
$"00FF020112022D299A3B3A49BCE2FF2ED4134A65A94C096A0000FFFF00000201"
|
||||
$"1202365425358147B6C63037AFB14669664AB9F30000FFFF0000020112023673"
|
||||
$"5235AC4EB7FB7138A81D481E6A48C2C50000FFFF00000F0241BE60B360BE60B3"
|
||||
$"60BE5FB360BE3EB364BE46B362BE2AB369BE17B371BE1FB36DBE03B379BDF3B3"
|
||||
$"85BDFCB37EBDE3B38EBDCEB3A0BDD9B398BDB8B3B1BD8BB3DDBDA4B3C5BD58B4"
|
||||
$"0EBCCDB4A0BD17B450BC93B4DBBC36B539BC61B50DBC35B537BC32B536BC34B5"
|
||||
$"37BBE6B50ABB0FB48BBB7EB4CEBA9EB448B9E8B3DDBA36B40AB9C1B3C5B987B3"
|
||||
$"A5B9A0B3B3B97AB39FB967B394B971B399B961B391B954B38CB95DB390B94FB3"
|
||||
$"89B942B385B94CB388B93FB382B92FB37EB939B381B926B37DB8FFB379B900B3"
|
||||
$"79B8E9B379B87FB3A4B8B1B37DB84CB3C8B82FB418B838B3FBB81FB453B826B4"
|
||||
$"89B825B466B827B4CDB841B5F9B82FB534B848B656B854B6F9B84EB6B1B85AB7"
|
||||
$"41B85CB776B85CB782B85CB75BB83AB7A7B860B772B814B7DBB767B88FB7CEB8"
|
||||
$"29B6E7B90DB65CB9D1B694B955B626BA4CB62ABB5AB62CBAB9B629BC54B606BC"
|
||||
$"9DB634BC1BB5CDBD3EB4B1BEF5B597BDA1B445BF96B3B0C089B3DDC033B31AC1"
|
||||
$"A4B318C3DAB2D2C2D1B371C536B61FC639B4ABC60FB641C680B698C6F2B65CC6"
|
||||
$"CFB698C6F2B69AC6F2B69AC6F2B71EC742B838C6F9B7BDC733B8B2C6BEB96CC5"
|
||||
$"E2B919C65DB99BC59FBA11C4C4B9D8C530BA78C400BB14C34ABAB4C3A1BB75C2"
|
||||
$"F2BD20C209BC0BC29ABDDEC1A6BED6C108BE5244BED6C121BED8C151BED9C139"
|
||||
$"BECCC24CBE29C3E9BE9AC307BDC3C4B6BC1DC63ABD84C4F7BB43C700BA57C7FA"
|
||||
$"BAB9C781B9F5C872B99DC966B9BCC8EBB961CA48B95ECBBBB955CB0830CBFDB9"
|
||||
$"65CC7FB962CC3DBFC3CC7F60CC7FC621CC7FCC7ECBDECC7ACA9BCC7CCB3CCC6F"
|
||||
$"C6D6CA63BE51CB9AC1F5C98736C731B8ADC899BA16C5F2B76EC2C4B648C477B6"
|
||||
$"A1C212B625BFF7B63643B625C013B634C04A28C02FB631C027B5E2BFE0B546C0"
|
||||
$"04B593BFAFB4D8BF5EB436BF81B47BBF4DB415BF30B3E0BF3FB3F8BF28B3D3BF"
|
||||
$"18B3BBBF22B3C9BF11B3B4BEFFB39DBF0CB3ABBEF8B398BEE2B385BEF1B390BE"
|
||||
$"DAB380BEC5B375BED1B37ABEB9B36EBE96B364BE96B364BE96B364BE95B364BE"
|
||||
$"95B364BE93B364BE93B364BE93B364BE93B364BE60B360BE60B360BE60B36002"
|
||||
$"23BCA6C6D2BCA6C6D2BE0FC58CBEDFC443BE70C523BF5BC34EBFA3C159BF97C2"
|
||||
$"6DBFAAC0AEBF80BFC2BF99BFDABF7ABFBBBF34BFE33FBFC7BEA9C048BCC3C154"
|
||||
$"BDD9C0C2BA90C277B95BC467BA2FC2CFB926C4CCB8C5C56FB8E2C542B83EC636"
|
||||
$"B702C644B780C68FB6CEC624B6A8C5B6B6B4C5FDB6A1C587B660C581B69CC584"
|
||||
$"B510C56EB3DDC3A7B426C4C2B3ACC2EDB465C0E9B3E0C1E1B481C0B1B55ABF67"
|
||||
$"B4F0C005B642BE10B6C7BCE0B689BD92B6F5BC5DB6F6BB5AB6F5BC55B6F7BA1A"
|
||||
$"B7F5B921B6F5BA1EB8CDB84DB928B776B928B7CEB928B757B90CB5E9B91BB6A4"
|
||||
$"B8EBB45DB8FFB446B8EBB446B907B446BAA6B53A31B4B4BB85B5C0BC54B62FBC"
|
||||
$"47B62FBC6128BD60B52BBCDBB5BABDF2B491BE6BB42BBE5EB428BE78B42EBF27"
|
||||
$"B59ABEC3B4C2BF5DB613BFCBB704BF95B68DBFDEB703C005B702BFF2B702C0F0"
|
||||
$"B6F1C29CB70FC229B6F9C42AB761C6A0B93DC57CB818C7F0BA8FC9A0BE92C8CC"
|
||||
$"BC13CACFC21CCBAECA9DCBA3C6F5CBAFCAFBCBB15ECBB0CB56C5D85EBA295EC0"
|
||||
$"015EBA21CB0FBA61C99A32CA68BA97C8CBBCA6C6D2BAF4C858BCA6C6D20215C8"
|
||||
$"1C5EC81C5EC80FCB23C7DAC9A7C805CA9DC79EC84BC6E7C4FBC747C6A251C353"
|
||||
$"C5B5C054C61BC1ACC54FBEF9C4A1BD7F4DBDEFC457BD12C3C3BC5FC40EBCB4C3"
|
||||
$"79BC0DC2D8BB87C32B36C285BB4BC1C8BAF0C22BBB19C195BADDC120BAC444BA"
|
||||
$"D2C13EBADEC177BB1CC15CBAF6C19EBB66C1B9BC18C1B5BBBAC1BCBC74C184BD"
|
||||
$"41C1ABBCD8C15CBDA9C0C1BE85C11DBE17C0683EBF5CBFD2BFF2BF64BF69BFCD"
|
||||
$"BF80BFC2BF7EBFBFBF99BFDABFA3C159BFAAC0AEBF97C26DBEE1C443BF5BC34E"
|
||||
$"BE70C523BCA6C6D2BE0FC58CBAF4C858BA61C99ABA97C8CB32CA68BA295EBA21"
|
||||
$"CB0FBECF5EC81C5EC3755EC81C5E021CBE6BB42BBE6BB42BBE5EB428BD60B52B"
|
||||
$"BDF2B491BCDBB5BABC54B62FBC6128BC47B62FBAA6B53ABB85B5C031B4B4B8FF"
|
||||
$"B446B907B446B8EBB446B90CB5E9B8EBB45DB91BB6A4B928B776B928B757B928"
|
||||
$"B7CEB7F5B921B8CDB84DB6F5BA1EB6F6BB5AB6F7BA1AB6F5BC55B6C7BCE0B6F5"
|
||||
$"BC5DB689BD92B55ABF67B642BE10B4F0C005B465C0E9B481C0B1B3E0C1E1B3DD"
|
||||
$"C3A7B3ACC2EEB426C4C2B660C581B510C56EB680C583B697C58AB68FC583B74F"
|
||||
$"C477B90545B815C32CB9FCC041BC10BD70BB07BEB8BC94BCCCBD99BBBBBD18BC"
|
||||
$"36BE19BB41BF0DBAA0BE96BADFBF49BA82BFBBBA5FBF82BA6BBFF3BA52C05CBA"
|
||||
$"59C028BA50C090BA6143BA94C0C2BA75C103BA9FC120BAC4C110BAB6C125BAC5"
|
||||
$"C130BAC7C12ABAC6C0BBB986BFCEB704C043B846BFCDB704BFCBB704BFCDB704"
|
||||
$"BF95B68BBF27B59ABF5DB613BEC4B4C2BE6BB42BBE78B42EBE6BB42B0207BFCE"
|
||||
$"B704BFCEB704C063B85EC18FBB10C0F9B9B7C1C2BB1DC2BCBB74C28DBB61C6B9"
|
||||
$"BBACC6A0B93DCB98BF33C57CB818C29CB70FC42AB761C229B6F9C005B702C0F0"
|
||||
$"B6F1BFF3B702BFCEB704BFDFB703BFCEB7040207BCA6C6D2BCA6C6D2474ACB64"
|
||||
$"C69E5149CB91C805CBAECA9DCBABC963CBAFCAFBCBB15ECBB0CB56C5D85EBA29"
|
||||
$"5EC0015EBA21CB0FBA61C99A32CA68BA97C8CBBCA6C6D2BAF4C858BCA6C6D206"
|
||||
$"04BFB67CC579B67CC579B7C1C49BB900C2AFB8F9C22FB906C32EB6F5C5CDB841"
|
||||
$"C6ABB5AA4DB67CC5790211BD5BC297BD5BC297BDC5C279BEE5C244BE49C25EBF"
|
||||
$"83C22BC0E8C21FC02EC21FC19DC21FC2AAC26CC234C238C323C29CC3C4C33EC3"
|
||||
$"81C2E1C40BC399C45BC485C43EC405C478C502C487C626C487C58DC487C7BCC4"
|
||||
$"87CAE7C487C9514ACAE746CAE7C2EFCAE746C96B46C67346C7EF46C5A0C1DDC4"
|
||||
$"ABC20BC508C1AFC44FC0C2C421C151C421C097C421C040C424C06D4BC018C428"
|
||||
$"BFBFC434BFEEC42CBFBFC66FBFBFCAE7BFBFC8ACBEF3CAE7BD5BCAE7BE27CAE7"
|
||||
$"BD5BC821BD5BC297BD5BC55BBD5BC2970211BE27C363BE27C363BE91C345BFB1"
|
||||
$"C310BF16C32AC050C2F7C1B4C2EBC0FAC2EBC269C2EBC376C338C300C304C3EF"
|
||||
$"C368C490C40AC44DC3ADC4D7C465C527C551C50AC4D1C544C5CE4EC6F24EC659"
|
||||
$"4EC8454ECAE74EC9964CCAE748CAE74ACAE748C9C548C77F48C8A148C6B9C2A9"
|
||||
$"C5D4C2D7C62BC27BC57FC18EC553C21DC553C163C553C10CC557C1394EC0E4C5"
|
||||
$"5A42C565C0BAC55E42C73A42CAE742C91140CAE73CCAE73ECAE73CC866BE27C3"
|
||||
$"63BE27C5E4BE27C3630206B669C28FB669C28FB669C25DB613C207B642C21EB5"
|
||||
$"8645B4F5C338B507C245B4F1C374B4F7C3BEB4F3C3B2B503C3DAB59DC370B507"
|
||||
$"C3D7B632C309B669C28FB669C2CAB669C28F0207BAE6BC94BAE6BC94BC1EBB5D"
|
||||
$"BD8EB8BBBD8EB948BD8EB89BBD1AB854BD5AB86DBBF7B7E7B988B975BA7DB85F"
|
||||
$"B902BA0EB763BDFCB82DBAE5B751BE42B7F5BEBCB6C13FB92ABE1DBAE6BC94B9"
|
||||
$"EDBD8CBAE6BC940207B9EABBF2B9EABBF2BA4CBB90BABFBABCBABFBAE9BABFBA"
|
||||
$"B2BA9BBA9CBAAEBAA3BA40BA79B97BBAF7B9C8BA9EB952BB27B85BBCCCB85BBC"
|
||||
$"B7B85BBCE3B8FCBC9EB89BBCCFB95EBC6CB9EABBF2B99CBC3FB9EABBF2020FC0"
|
||||
$"E42CC0E42CC0BFB7C942B801C09DB7E0C07BB825C096B86CC080B84DC0ADB889"
|
||||
$"C0F8B893C0D4B899C2D4B862C515B9BAC413B8E0C617BA94C789BD20C6D6BBD2"
|
||||
$"C7CFBDA0C8EFC1C5C869BF62C977C428CA19CA85C9F2C73ACA1BCAABCA4FCADD"
|
||||
$"CA30CACCCA6FCAEDCAB5CAD7CA97CAEBCAD4CAC4CAE5CA7DCAE7CAA1CABDC722"
|
||||
$"59C19ACA3FC408C92DBF2BC83CBCC0C89FBD76C786BB6DC599B920C6BEBA17C4"
|
||||
$"73B827C0E42CC2EEB794C0E42C020AC70ABC69C70ABC69C1BB3BC864C462C353"
|
||||
$"50C8CFC440C982C3CEC930C411C983C3CDC984C3CCC983C3CCC985C3CAC987C3"
|
||||
$"C7C986C3C9C9D4C384CA37C2CDCA13C32DCA59C272CA1945CA19C220C9B33FC8"
|
||||
$"5ABC98C9B33DC85ABC98C859BC98C859BC98C7F2BC76C70ABC69C785BC69C70A"
|
||||
$"BC690220C6E2C242C6E2C242C740C242C7A5C216C782C234C7CCC1F8C7DFC1AB"
|
||||
$"C7DFC1D6C7DFC141C6C8C10CC782C10CC690C10CC622C10CC659C10CC622C0A1"
|
||||
$"C622BFC8C622C035C659BFC8C6C8BFC8C690BFC8C705BFC8C75FBFA5C738BFBD"
|
||||
$"C785BF8DC798BF35C798BF67C798BEE3C6EBBEB9C75FBEB9C6ADBEB9C635BED9"
|
||||
$"C66FBEC3C5FABEEEC587BF1BC5BFBF03C555BEB4C4F0BDE5C523BE4CC532BDBA"
|
||||
$"C5E5BD79C584BD98C64ABD5AC709BD4AC6ABBD4AC774BD4AC814BD6CC7CDBD54"
|
||||
$"C85EBD84C8C6BDCEC89ABDA5C8F1BDF5C922BE5CC911BE24C935BE91C93DBF04"
|
||||
$"C93DBECAC93DBF3EC916BFA5C931BF73C8FEBFD4C89AC038C8D4C005C8EEC05D"
|
||||
$"58C0D7C92CC092C975C117C988C1B0C988C160C988C1FAC966C27CC97DC23EC9"
|
||||
$"4EC2BBC8F1C321C927C2F1C8BCC34DC821C38BC878C370C7CCC3A5C6E7C3B4C7"
|
||||
$"63C3B4C68DC3B4C5C5C399C62EC3AAC562C384C4D6C348C511C36AC4F5C2D4C5"
|
||||
$"34C1EAC515C25EC58CC210C616C236C5D7C229C653C23EC6E2C242C698C242C6"
|
||||
$"E2C2420F0A000100000A010101000A020102000A030103000A040104000A0501"
|
||||
$"05000A060106000A010107000A000108000A000109000A07010A000A00010B00"
|
||||
$"0A00010C000A01010D000A00010E00"
|
||||
};
|
Binary file not shown.
After Width: | Height: | Size: 9.8 KiB |
Binary file not shown.
After Width: | Height: | Size: 4.5 KiB |
|
@ -0,0 +1,302 @@
|
|||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<!-- Created with Inkscape (http://www.inkscape.org/) -->
|
||||
|
||||
<svg
|
||||
xmlns:dc="http://purl.org/dc/elements/1.1/"
|
||||
xmlns:cc="http://creativecommons.org/ns#"
|
||||
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
||||
xmlns:svg="http://www.w3.org/2000/svg"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
xmlns:xlink="http://www.w3.org/1999/xlink"
|
||||
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
|
||||
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
|
||||
width="63.999996"
|
||||
height="63.999996"
|
||||
viewBox="0 0 16.933332 16.933333"
|
||||
version="1.1"
|
||||
id="svg8"
|
||||
inkscape:version="0.92.5 (2060ec1f9f, 2020-04-08)"
|
||||
sodipodi:docname="logo.svg"
|
||||
inkscape:export-filename="logo-64x64.png"
|
||||
inkscape:export-xdpi="96.000008"
|
||||
inkscape:export-ydpi="96.000008">
|
||||
<title
|
||||
id="title1733">n³ logo</title>
|
||||
<defs
|
||||
id="defs2">
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient4258">
|
||||
<stop
|
||||
style="stop-color:#000000;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop4254" />
|
||||
<stop
|
||||
style="stop-color:#000000;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop4256" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient3891">
|
||||
<stop
|
||||
style="stop-color:#000000;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop3887" />
|
||||
<stop
|
||||
style="stop-color:#000000;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop3889" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient3746">
|
||||
<stop
|
||||
style="stop-color:#000000;stop-opacity:0"
|
||||
offset="0"
|
||||
id="stop3742" />
|
||||
<stop
|
||||
id="stop3750"
|
||||
offset="0.68665242"
|
||||
style="stop-color:#000000;stop-opacity:0" />
|
||||
<stop
|
||||
style="stop-color:#000000;stop-opacity:1"
|
||||
offset="1"
|
||||
id="stop3744" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient3628">
|
||||
<stop
|
||||
style="stop-color:#000000;stop-opacity:1"
|
||||
offset="0"
|
||||
id="stop3624" />
|
||||
<stop
|
||||
style="stop-color:#000000;stop-opacity:0"
|
||||
offset="1"
|
||||
id="stop3626" />
|
||||
</linearGradient>
|
||||
<radialGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient3628"
|
||||
id="radialGradient4190"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
gradientTransform="matrix(0.10643412,0.08213184,-0.08695471,0.11268405,2.5028417,-19.507024)"
|
||||
cx="80.745285"
|
||||
cy="31.199144"
|
||||
fx="80.745285"
|
||||
fy="31.199144"
|
||||
r="17.514044" />
|
||||
<radialGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient3628"
|
||||
id="radialGradient4200"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
gradientTransform="matrix(0.1591284,-0.22144644,0.05150741,0.03701252,-10.674157,4.5498963)"
|
||||
cx="63.691868"
|
||||
cy="24.91503"
|
||||
fx="63.691868"
|
||||
fy="24.91503"
|
||||
r="16.80954" />
|
||||
<radialGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient3746"
|
||||
id="radialGradient4206"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
gradientTransform="matrix(0.08312121,-0.16218012,0.2763752,0.1416496,-5.8976633,2.3429863)"
|
||||
cx="109.63785"
|
||||
cy="27.735554"
|
||||
fx="109.63785"
|
||||
fy="27.735554"
|
||||
r="14.917971" />
|
||||
<radialGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient3891"
|
||||
id="radialGradient4208"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
gradientTransform="matrix(0.77009845,-0.00589491,0.0032956,0.4305302,1.4732687,-112.12628)"
|
||||
cx="10.145939"
|
||||
cy="261.29977"
|
||||
fx="10.145939"
|
||||
fy="261.29977"
|
||||
r="7.9343286" />
|
||||
<radialGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient4258"
|
||||
id="radialGradient4260"
|
||||
cx="38.219185"
|
||||
cy="-11.155752"
|
||||
fx="38.219185"
|
||||
fy="-11.155752"
|
||||
r="2.5266471"
|
||||
gradientTransform="matrix(0.41700468,-0.5564057,0.25660676,0.1923169,-8.5901303,12.321222)"
|
||||
gradientUnits="userSpaceOnUse" />
|
||||
<radialGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient3891"
|
||||
id="radialGradient4271"
|
||||
cx="36.437771"
|
||||
cy="11.167927"
|
||||
fx="36.437771"
|
||||
fy="11.167927"
|
||||
r="0.92064488"
|
||||
gradientTransform="matrix(0.79726776,-1.0594042,0.6692442,0.50364803,-33.972333,27.585938)"
|
||||
gradientUnits="userSpaceOnUse" />
|
||||
</defs>
|
||||
<sodipodi:namedview
|
||||
id="base"
|
||||
pagecolor="#ffffff"
|
||||
bordercolor="#666666"
|
||||
borderopacity="1.0"
|
||||
inkscape:pageopacity="0.0"
|
||||
inkscape:pageshadow="2"
|
||||
inkscape:zoom="1"
|
||||
inkscape:cx="43.627536"
|
||||
inkscape:cy="44.431591"
|
||||
inkscape:document-units="mm"
|
||||
inkscape:current-layer="layer2"
|
||||
showgrid="true"
|
||||
units="px"
|
||||
inkscape:snap-bbox="true"
|
||||
inkscape:snap-bbox-midpoints="false"
|
||||
inkscape:bbox-nodes="true"
|
||||
inkscape:object-nodes="false"
|
||||
inkscape:snap-global="true"
|
||||
inkscape:snap-nodes="true"
|
||||
inkscape:window-width="1918"
|
||||
inkscape:window-height="1060"
|
||||
inkscape:window-x="0"
|
||||
inkscape:window-y="18"
|
||||
inkscape:window-maximized="0"
|
||||
fit-margin-top="0"
|
||||
fit-margin-left="0"
|
||||
fit-margin-right="0"
|
||||
fit-margin-bottom="0"
|
||||
showguides="false">
|
||||
<inkscape:grid
|
||||
type="xygrid"
|
||||
id="grid815"
|
||||
empspacing="2"
|
||||
dotted="true"
|
||||
originx="0"
|
||||
originy="0" />
|
||||
<inkscape:grid
|
||||
type="xygrid"
|
||||
id="grid1158"
|
||||
spacingx="16.933333"
|
||||
spacingy="16.933333"
|
||||
empcolor="#3fff3f"
|
||||
empopacity="0.25098039"
|
||||
enabled="true"
|
||||
color="#52ff3f"
|
||||
opacity="0.1254902"
|
||||
originx="0"
|
||||
originy="0" />
|
||||
</sodipodi:namedview>
|
||||
<metadata
|
||||
id="metadata5">
|
||||
<rdf:RDF>
|
||||
<cc:Work
|
||||
rdf:about="">
|
||||
<dc:format>image/svg+xml</dc:format>
|
||||
<dc:type
|
||||
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
|
||||
<dc:title>n³ logo</dc:title>
|
||||
<dc:creator>
|
||||
<cc:Agent>
|
||||
<dc:title>Léo Villeveygoux</dc:title>
|
||||
</cc:Agent>
|
||||
</dc:creator>
|
||||
</cc:Work>
|
||||
</rdf:RDF>
|
||||
</metadata>
|
||||
<g
|
||||
inkscape:groupmode="layer"
|
||||
id="layer2"
|
||||
inkscape:label="fg"
|
||||
transform="translate(1.6666665e-6,16.933336)"
|
||||
style="display:inline">
|
||||
<path
|
||||
sodipodi:nodetypes="ccccccccccccccccscccsccccccccccccccccscccccccccccccscccccsccsccccc"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path4096"
|
||||
d="m 7.5563837,-16.683514 c -6.37e-4,4e-5 -0.06582,0.008 -0.08984,0.0137 -0.04805,0.0106 -0.07759,0.0228 -0.101563,0.0332 -0.04795,0.0209 -0.07078,0.0351 -0.0918,0.0488 -0.04203,0.0274 -0.06833,0.0495 -0.0957,0.0723 -0.05474,0.0455 -0.10969,0.0967 -0.175781,0.16016 -0.132182,0.127 -0.300521,0.29823 -0.492188,0.50195 -0.146719,0.15595 -0.277344,0.28701 -0.388672,0.39649 -0.0057,-0.003 -0.0078,-0.004 -0.01367,-0.008 -0.197393,-0.11237 -0.466421,-0.2688 -0.753907,-0.4414 -0.292561,-0.17566 -0.563176,-0.33604 -0.765625,-0.45313 -0.101224,-0.0585 -0.185684,-0.10714 -0.25,-0.14258 -0.03216,-0.0177 -0.05714,-0.0313 -0.08398,-0.0449 -0.01342,-0.007 -0.02769,-0.0122 -0.04883,-0.0215 -0.01057,-0.005 -0.02139,-0.0114 -0.04492,-0.0195 -0.01177,-0.004 -0.02683,-0.008 -0.05078,-0.0137 -0.02395,-0.006 -0.124654,-0.0156 -0.125,-0.0156 -0.05674,0 -0.203301,0.0121 -0.333985,0.10937 -0.130683,0.0973 -0.184045,0.2292 -0.205078,0.30469 -0.04207,0.15099 -0.02811,0.20268 -0.02539,0.29102 0.0054,0.17668 0.02754,0.44302 0.07031,0.95703 0.02009,0.24144 0.03761,0.47757 0.05078,0.66211 0.01317,0.18453 0.02149,0.35714 0.02149,0.32617 -2.5e-5,-0.0716 0.0084,-0.0136 -0.08984,0.12305 -0.09824,0.13666 -0.280681,0.34121 -0.548828,0.60546 -0.331583,0.32677 -0.546477,0.51342 -0.689453,0.83204 -0.142977,0.31862 -0.12766,0.605 -0.128907,1.01953 -0.0019,0.65046 0.02339,0.50097 -0.0957,0.84179 -0.144761,0.41429 -0.289011,0.6739003 -0.884765,1.5566403 -0.27946103,0.41409 -0.54683003,0.82021 -0.66601603,1.04493 -0.389514,0.73442 -0.574283,1.51442 -0.394531,2.20507 0.234069,0.89938 1.04359803,1.46551 2.00976503,1.57227 0.08937,0.18231 0.157509,0.38673 0.316407,0.48242 h 0.002 c 0.344505,0.20741 0.757366,0.16421 1.074218,0.0137 0.316853,-0.15053 0.584433,-0.40119 0.802735,-0.72265 0.11807,-0.17388 0.279753,-0.46209 0.423828,-0.73828 0.267813,-0.5134 0.424453,-0.75918 0.673828,-0.98438 0.249375,-0.2252 0.638049,-0.4572 1.359375,-0.83203 0.492658,-0.25601 0.795852,-0.45655 1.134766,-0.66797 -3.2e-5,0.0656 0.0067,0.12864 0.0039,0.18945 -0.02949,0.65113 -0.155996,1.13801 -0.449219,1.72266 -0.266512,0.53141 -0.429772,0.70223 -1.361329,1.54102 -0.567672,0.51114 -0.922548,0.84685 -1.177734,1.16015 -0.255186,0.31331 -0.40187,0.6268 -0.484375,0.94336 -0.153164,0.58764 -0.184601,1.08693002 -0.164063,1.55274002 L 4.2498067,-3.675972e-6 H 16.933332 L 16.919662,-1.2538237 c -0.0264,-2.50458 -0.581284,-5.74387 -1.388672,-8.16016 -0.567382,-1.6980103 -1.186678,-2.8095203 -2.121093,-3.7480403 -0.824138,-0.82775 -1.808365,-1.36141 -2.937501,-1.58985 -0.460672,-0.0932 -1.2090663,-0.0911 -1.8593753,-0.0488 l 0.216796,-0.0137 -0.277343,-0.60742 c -0.129838,-0.28446 -0.245022,-0.52486 -0.335938,-0.70312 -0.04546,-0.0891 -0.0838,-0.16151 -0.121094,-0.22461 -0.01865,-0.0315 -0.03654,-0.0597 -0.06445,-0.0977 -0.01396,-0.019 -0.02894,-0.0405 -0.0625,-0.0742 -0.01678,-0.0169 -0.03866,-0.0381 -0.07617,-0.0644 -0.01876,-0.0132 -0.04084,-0.0276 -0.07227,-0.043 -0.03143,-0.0154 -0.12448,-0.0429 -0.125,-0.043 h -0.0039 l -0.0019,-0.002 c -5.15e-4,-10e-5 -0.132175,-0.01 -0.132812,-0.01 z"
|
||||
style="color:#000000;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:10.58333302px;line-height:80.00000119%;font-family:'DejaVu Sans';-inkscape-font-specification:'DejaVu Sans';font-variant-ligatures:normal;font-variant-position:normal;font-variant-caps:normal;font-variant-numeric:normal;font-variant-alternates:normal;font-feature-settings:normal;text-indent:0;text-align:start;text-decoration:none;text-decoration-line:none;text-decoration-style:solid;text-decoration-color:#000000;letter-spacing:0px;word-spacing:0px;text-transform:none;writing-mode:lr-tb;direction:ltr;text-orientation:mixed;dominant-baseline:auto;baseline-shift:baseline;text-anchor:start;white-space:normal;shape-padding:0;clip-rule:nonzero;display:inline;overflow:visible;visibility:visible;opacity:1;isolation:auto;mix-blend-mode:normal;color-interpolation:sRGB;color-interpolation-filters:linearRGB;solid-color:#000000;solid-opacity:1;vector-effect:none;fill:#ffffff;fill-opacity:1;fill-rule:nonzero;stroke:none;stroke-width:1.05833328;stroke-linecap:square;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1;paint-order:markers stroke fill;color-rendering:auto;image-rendering:auto;shape-rendering:auto;text-rendering:auto;enable-background:accumulate" />
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path4098"
|
||||
d="m 6.4080867,-3.7690437 c 0.938534,-0.84507 1.188659,-1.11552 1.48007,-1.69657 0.320921,-0.63988 0.47318,-1.22312 0.505483,-1.9363 0.02009,-0.44367 -0.02591,-0.99383 -0.08833,-1.05625 -0.01983,-0.0198 -0.09943,0.0146 -0.196664,0.0851 -0.362858,0.26298 -0.902924,0.58065 -1.625708,0.95624 -1.458811,0.75805 -1.708252,0.98331 -2.259881,2.04078 -0.136798,0.26224 -0.312882,0.57127 -0.391298,0.68675 -0.348405,0.51305 -0.842285,0.74905 -1.167444,0.55329 -0.136991,-0.0825 -0.203307,-0.18758 -0.23386,-0.37066 -0.0206,-0.1234 -0.02893,-0.12948 -0.189186,-0.13815 -0.869164,-0.047 -1.47390803,-0.49276 -1.66510103,-1.22739 -0.125725,-0.48307 0.0075,-1.1762 0.35022,-1.82239 0.076,-0.14329 0.36220403,-0.59246 0.63600503,-0.99816 0.601277,-0.89093 0.78603,-1.21845 0.946654,-1.6781303 0.120217,-0.34405 0.12288,-0.36238 0.124815,-1.01425 0.0025,-0.83103 -0.0022,-0.82067 0.662064,-1.47528 0.558243,-0.55015 0.795236,-0.87983 0.795158,-1.10615 -2.8e-5,-0.0813 -0.0332,-0.54616 -0.07371,-1.033 -0.08546,-1.02692 -0.08733,-1.08802 -0.03345,-1.08802 0.02217,0 0.515642,0.2854 1.096601,0.63421 0.58096,0.34881 1.083868,0.63511 1.117573,0.63621 0.03371,10e-4 0.347056,-0.30174 0.696336,-0.67299 0.374566,-0.39812 0.657987,-0.67043 0.690965,-0.66387 0.03324,0.007 0.230015,0.39256 0.485181,0.95161 l 0.429268,0.94049 0.146868,-0.01 c 0.609325,-0.0396 1.4254303,-0.0214 1.7210693,0.0384 1.033646,0.20912 1.909331,0.68342 2.667218,1.44463 0.872014,0.87585 1.440968,1.88647 1.994305,3.5424503 0.784909,2.34901 1.335797,5.56889 1.361403,7.99842 l 0.0076,0.71920002 H 4.7566417 c -0.01888,-0.4282 0.0079,-0.85904002 0.147789,-1.39575002 0.139882,-0.53671 0.378578,-0.83142 1.503656,-1.84447 z"
|
||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:10.58333302px;line-height:80.00000119%;font-family:'DejaVu Sans';-inkscape-font-specification:'DejaVu Sans';letter-spacing:0px;word-spacing:0px;display:inline;fill:#2e3436;fill-opacity:1;stroke:none;stroke-width:1.05833328;stroke-linecap:square;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:markers stroke fill" />
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:10.58333302px;line-height:80.00000119%;font-family:'DejaVu Sans';-inkscape-font-specification:'DejaVu Sans';letter-spacing:0px;word-spacing:0px;display:inline;fill:url(#radialGradient4190);fill-opacity:1;stroke:none;stroke-width:1.05833328;stroke-linecap:square;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:markers stroke fill"
|
||||
d="m 14.019296,-0.52863368 c -0.03236,-0.37147 -0.05679,-0.71947002 -0.168981,-1.35909002 -0.15856,-0.90396 -0.383199,-2.00523 -0.634071,-3.1042 -0.25087,-1.09897 -0.528185,-2.19572 -0.792716,-3.09077 -0.264533,-0.89505 -0.516175,-1.58828 -0.715719,-1.8805 -0.190129,-0.2784503 -0.377891,-0.5254103 -0.572058,-0.7420803 -0.194167,-0.21666 -0.394798,-0.40292 -0.611333,-0.5612 -0.216532,-0.15828 -0.448667,-0.28843 -0.7058983,-0.39171 -0.131273,-0.0527 -0.29119,-0.0793 -0.436667,-0.11834 0.07747,0.0695 0.156587,0.13071 0.227892,0.22944 0.09939,0.19294 0.158695,0.41322 0.167431,0.65319 0.0087,0.23998 -0.03275,0.49928 -0.135908,0.77102 -0.103153,0.2717303 -0.267553,0.5556703 -0.503845,0.8438703 -0.233789,0.28516 -0.540714,0.57454 -0.925525,0.86093 0.03184,-0.0131 0.08412,-0.0497 0.09353,-0.0403 0.06242,0.0624 0.108457,0.6126 0.08837,1.05627 -0.0323,0.71318 -0.184474,1.29644 -0.505395,1.93632 -0.291411,0.58105 -0.541995,0.85146 -1.48053,1.69653 -1.125078,1.01305 -1.363385,1.30814 -1.503267,1.84485 -0.139889,0.53671 -0.166675,0.96758002 -0.147795,1.39578002 z"
|
||||
id="path4106" />
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path4116"
|
||||
d="m 7.5855797,-16.154034 c -0.03298,-0.007 -0.316348,0.26592 -0.690914,0.66404 -0.34928,0.37125 -0.662888,0.67383 -0.696598,0.67283 -0.0337,-10e-4 -0.536801,-0.28733 -1.117761,-0.63614 -0.58096,-0.34881 -1.074404,-0.63407 -1.096574,-0.63407 -0.05388,0 -0.05187,0.0609 0.03359,1.08779 0.04051,0.48684 0.07387,0.95171 0.0739,1.03301 7.7e-5,0.22632 -0.237058,0.55625 -0.795301,1.1064 -0.664264,0.65461 -0.659475,0.64381 -0.661975,1.47484 -0.0019,0.65187 -0.0048,0.67036 -0.125057,1.01441 -0.160624,0.4596803 -0.345435,0.7870003 -0.946712,1.6779303 -0.273801,0.4057 -0.55962,0.8551 -0.63562003,0.99839 -0.34272,0.64619 -0.476091,1.33956 -0.350366,1.82263 0.191193,0.73463 0.79585103,1.18032 1.66501403,1.22732 0.08533,0.005 0.123824,0.005 0.147795,0.0264 0.474897,-0.71432 0.990332,-1.57106 1.609204,-2.52181 0.642554,-0.98713 1.335583,-2.00634 2.022099,-2.85977 0.343258,-0.4267203 0.685028,-0.8121303 1.018026,-1.1312003 0.332998,-0.31907 0.65726,-0.57187 0.965832,-0.73381 0.154287,-0.081 0.304578,-0.13915 0.450102,-0.17156 0.145524,-0.0324 0.286173,-0.0389 0.421163,-0.0165 0.13499,0.0223 0.264371,0.0733 0.387056,0.15658 0.04214,0.0286 0.07884,0.0836 0.119373,0.11989 0.01427,0.004 0.02839,0.008 0.04289,0.0114 l -0.920357,-2.49752 -0.0047,5.1e-4 -0.428914,-0.94051 c -0.255166,-0.55905 -0.452002,-0.94436 -0.485242,-0.95136 z"
|
||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:10.58333302px;line-height:80.00000119%;font-family:'DejaVu Sans';-inkscape-font-specification:'DejaVu Sans';letter-spacing:0px;word-spacing:0px;display:inline;fill:url(#radialGradient4200);fill-opacity:1;stroke:none;stroke-width:1.05833328;stroke-linecap:square;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:markers stroke fill" />
|
||||
<path
|
||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:10.58333302px;line-height:80.00000119%;font-family:'DejaVu Sans';-inkscape-font-specification:'DejaVu Sans';letter-spacing:0px;word-spacing:0px;display:inline;fill:url(#radialGradient4206);fill-opacity:1;stroke:none;stroke-width:1.05833328;stroke-linecap:square;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:markers stroke fill"
|
||||
d="m 8.5043867,-14.262674 1.165911,2.68461 c 0.133392,0.0334 0.6612493,0.21144 0.7796483,0.25898 2.649479,0.14717 5.883653,2.4870503 2.584913,-1.46978 -0.757881,-0.76121 -1.633374,-1.23575 -2.667019,-1.44487 -0.29564,-0.0598 -1.1120183,-0.0778 -1.7213433,-0.0382 z"
|
||||
id="path4122"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="ccccccc" />
|
||||
<path
|
||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:10.58333302px;line-height:80.00000119%;font-family:'DejaVu Sans';-inkscape-font-specification:'DejaVu Sans';letter-spacing:0px;word-spacing:0px;display:inline;fill:url(#radialGradient4208);fill-opacity:1;stroke:none;stroke-width:1.05833328;stroke-linecap:square;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:markers stroke fill"
|
||||
d="m 6.4080867,-3.7690437 c 3.9106623,-2.0517737 6.5564953,-2.316357 9.7896183,-0.1353155 0.116365,0.9327131 0.184394,1.8392243 0.193006,2.6563355 l 0.0076,0.71920002 H 4.7566417 c -0.01888,-0.4282 0.0079,-0.85904002 0.147789,-1.39575002 0.139882,-0.53671 0.378578,-0.83142 1.503656,-1.84447 z"
|
||||
id="path4124"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="ccccccc" />
|
||||
<path
|
||||
style="display:inline;opacity:0.33200001;fill:url(#radialGradient4271);fill-opacity:1;fill-rule:evenodd;stroke:none;stroke-width:0.26458332px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
d="m 2.3150987,-4.6632687 c 0.84336,-0.578776 1.653646,-2.182813 1.670183,-1.852083 0.01654,0.330729 -0.496094,2.645833 -1.35599,2.067057 -0.859896,-0.578776 -0.314193,-0.214974 -0.314193,-0.214974 z"
|
||||
id="path4262"
|
||||
inkscape:connector-curvature="0" />
|
||||
<path
|
||||
sodipodi:nodetypes="ccscccsccscsccccc"
|
||||
inkscape:connector-curvature="0"
|
||||
d="m 6.8791644,-6.5799967 c 0.277182,-0.0747 0.617361,-0.14533 1.020535,-0.21177 0.411575,-0.0665 0.856747,-0.0997 1.335516,-0.0997 0.470371,0 0.8609466,0.0664 1.1717256,0.19932 0.310781,0.12456 0.554366,0.30725 0.730754,0.54808 0.18479,0.23253 0.314982,0.51489 0.390577,0.8470599 0.0756,0.32387 0.113393,0.68512 0.113393,1.08374 v 3.1548598 h -1.5875 v -2.9555598 c 0,-0.5481 -0.06013,-0.94256 -0.1803996,-1.18338 -0.120264,-0.2408299 -0.364802,-0.3612399 -0.733616,-0.3612399 -0.112248,0 -0.224495,0.004 -0.336742,0.0125 -0.10423,0.008 -0.216478,0.0208 -0.336743,0.0373 v 4.4503697 h -1.5875 z"
|
||||
style="font-style:normal;font-variant:normal;font-weight:bold;font-stretch:normal;font-size:14.11111069px;line-height:80.00000119%;font-family:'Ubuntu Mono';-inkscape-font-specification:'Ubuntu Mono Bold';letter-spacing:0px;word-spacing:0px;fill:#2e3436;fill-opacity:1;stroke:none;stroke-width:0.23356323px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="path4273" />
|
||||
<path
|
||||
sodipodi:nodetypes="ccscccsccscsccccc"
|
||||
inkscape:connector-curvature="0"
|
||||
d="m 7.4083317,-6.0508267 c 0.277182,-0.0747 0.617361,-0.14533 1.020535,-0.21177 0.411575,-0.0665 0.856747,-0.0997 1.335516,-0.0997 0.4703713,0 0.8609463,0.0664 1.1717253,0.19932 0.310781,0.12456 0.554366,0.30725 0.730754,0.54808 0.18479,0.23253 0.314982,0.5148899 0.390577,0.8470599 0.0756,0.32387 0.113393,0.68512 0.113393,1.08374 v 2.6257298 h -1.5875 v -2.2633598 c 0,-0.51127 -0.06013,-0.87922 -0.180399,-1.10385 -0.120264,-0.22465 -0.364802,-0.33697 -0.7336163,-0.33697 -0.112248,0 -0.224495,0.004 -0.336742,0.0117 -0.10423,0.007 -0.216478,0.0194 -0.336743,0.0348 v 3.6577098 h -1.5875 z"
|
||||
style="font-style:normal;font-variant:normal;font-weight:bold;font-stretch:normal;font-size:14.11111069px;line-height:80.00000119%;font-family:'Ubuntu Mono';-inkscape-font-specification:'Ubuntu Mono Bold';letter-spacing:0px;word-spacing:0px;fill:#ffffff;fill-opacity:1;stroke:none;stroke-width:0.23356323px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="path4158" />
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path4160"
|
||||
d="m 2.2657997,-6.5970811 c 2.39e-4,-0.13158 -0.102021,-0.29549 -0.222752,-0.3571395 -0.367285,-0.18754 -0.694817,0.1635095 -0.738403,0.7914195 -0.01108,0.15956 -0.0093,0.31791 0.0038,0.35187 0.0276,0.071 0.04155,0.0639 0.42986,-0.20266 0.388306,-0.26657 0.527201,-0.43437 0.527446,-0.58349 z"
|
||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:10.58333302px;line-height:80.00000119%;font-family:'DejaVu Sans';-inkscape-font-specification:'DejaVu Sans';letter-spacing:0px;word-spacing:0px;fill:#ffffff;fill-opacity:1;stroke:none;stroke-width:1.05833328;stroke-linecap:square;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:markers stroke fill" />
|
||||
<path
|
||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:10.58333302px;line-height:80.00000119%;font-family:'DejaVu Sans';-inkscape-font-specification:'DejaVu Sans';letter-spacing:0px;word-spacing:0px;opacity:0.44600004;fill:url(#radialGradient4260);fill-opacity:1;stroke:none;stroke-width:3.37220645;stroke-linecap:square;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:markers stroke fill"
|
||||
d="m 5.2460787,-10.568226 c 0.812188,-0.809811 1.765374,-2.190004 1.765374,-2.556274 0,-0.0838 -0.135642,-0.203925 -0.301459,-0.267015 -0.752294,-0.286133 -1.733457,0.02549 -2.369685,0.748534 -0.347846,0.396158 -0.900949,0.953943 -1.423035,3.0038925 -0.04718,0.1852661 -0.424024,0.9086143 0.377177,0.4985965 0.801204,-0.4100179 1.308944,-0.7869297 1.951628,-1.427734 z"
|
||||
id="path4252"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="ssccscs" />
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path4162"
|
||||
d="m 4.5914317,-10.992111 c 0.254897,-0.254151 0.554045,-0.687311 0.554045,-0.802261 0,-0.0263 -0.04257,-0.064 -0.09461,-0.0838 -0.2361,-0.0898 -0.544028,0.008 -0.743702,0.23492 -0.109168,0.12433 -0.747614,1.164311 -0.747614,1.217801 0,0.06 0.167933,0.0101 0.419382,-0.11858 0.25145,-0.12868 0.410799,-0.24697 0.612499,-0.44808 z"
|
||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:10.58333302px;line-height:80.00000119%;font-family:'DejaVu Sans';-inkscape-font-specification:'DejaVu Sans';letter-spacing:0px;word-spacing:0px;fill:#ffffff;fill-opacity:1;stroke:none;stroke-width:1.05833328;stroke-linecap:square;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:markers stroke fill" />
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path4164"
|
||||
d="m 9.2282597,-13.755752 a 0.26460981,0.26460981 0 1 0 0.05273,0.52539 c 1.2306523,-0.12455 2.0604593,0.20175 2.7285163,0.76758 0.668056,0.56582 1.165386,1.39097 1.630859,2.255861 0.179199,0.3329602 0.577259,1.4975302 0.927734,3.0839804 0.350476,1.5864495 0.671479,3.6240594 0.771485,5.8124992 a 0.26490778,0.26490778 0 1 0 0.529297,-0.0234 c -0.101686,-2.2251898 -0.428845,-4.2894697 -0.785157,-5.9023392 -0.356311,-1.6128702 -0.723527,-2.7469202 -0.978515,-3.2207004 -0.472697,-0.878311 -0.99272,-1.763511 -1.753906,-2.408211 -0.761187,-0.6447 -1.771873,-1.02737 -3.1230473,-0.89062 z"
|
||||
style="color:#000000;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:10.58333302px;line-height:80.00000119%;font-family:'DejaVu Sans';-inkscape-font-specification:'DejaVu Sans';font-variant-ligatures:normal;font-variant-position:normal;font-variant-caps:normal;font-variant-numeric:normal;font-variant-alternates:normal;font-feature-settings:normal;text-indent:0;text-align:start;text-decoration:none;text-decoration-line:none;text-decoration-style:solid;text-decoration-color:#000000;letter-spacing:0px;word-spacing:0px;text-transform:none;writing-mode:lr-tb;direction:ltr;text-orientation:mixed;dominant-baseline:auto;baseline-shift:baseline;text-anchor:start;white-space:normal;shape-padding:0;clip-rule:nonzero;display:inline;overflow:visible;visibility:visible;opacity:1;isolation:auto;mix-blend-mode:normal;color-interpolation:sRGB;color-interpolation-filters:linearRGB;solid-color:#000000;solid-opacity:1;vector-effect:none;fill:#ffffff;fill-opacity:1;fill-rule:evenodd;stroke:none;stroke-width:0.5291667;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1;color-rendering:auto;image-rendering:auto;shape-rendering:auto;text-rendering:auto;enable-background:accumulate" />
|
||||
<path
|
||||
sodipodi:nodetypes="ccccccccccc"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path4275"
|
||||
d="m 13.309647,-10.683461 c -3.5259213,0.8942402 -2.467588,6.4504898 0.896553,5.2949099 0.277432,-0.0861 0.529922,-0.20786 0.742188,-0.38476 l 0.0059,-0.006 0.0078,-0.008 c 0.200661,-0.17837 0.36145,-0.4014 0.457031,-0.65235 0.08874,-0.23296 -0.07914,-0.44979 -0.07914,-0.7037295 -0.264584,-1.5875002 -0.264584,-2.1166602 -1.157186,-3.4173504 -0.0012,-3.9e-4 -0.0027,3.9e-4 -0.0039,0 -0.266042,-0.0881 -0.551145,-0.12305 -0.86914,-0.12305 z"
|
||||
style="color:#000000;font-style:normal;font-variant:normal;font-weight:bold;font-stretch:normal;font-size:14.11111069px;line-height:80.00000119%;font-family:'Ubuntu Mono';-inkscape-font-specification:'Ubuntu Mono Bold';font-variant-ligatures:normal;font-variant-position:normal;font-variant-caps:normal;font-variant-numeric:normal;font-variant-alternates:normal;font-feature-settings:normal;text-indent:0;text-align:start;text-decoration:none;text-decoration-line:none;text-decoration-style:solid;text-decoration-color:#000000;letter-spacing:0px;word-spacing:0px;text-transform:none;writing-mode:lr-tb;direction:ltr;text-orientation:mixed;dominant-baseline:auto;baseline-shift:baseline;text-anchor:start;white-space:normal;shape-padding:0;clip-rule:nonzero;display:inline;overflow:visible;visibility:visible;opacity:1;isolation:auto;mix-blend-mode:normal;color-interpolation:sRGB;color-interpolation-filters:linearRGB;solid-color:#000000;solid-opacity:1;vector-effect:none;fill:#2e3436;fill-opacity:1;fill-rule:nonzero;stroke:none;stroke-width:1.16429496;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1;paint-order:markers stroke fill;color-rendering:auto;image-rendering:auto;shape-rendering:auto;text-rendering:auto;enable-background:accumulate" />
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path4168"
|
||||
style="font-style:normal;font-variant:normal;font-weight:bold;font-stretch:normal;font-size:14.11111069px;line-height:80.00000119%;font-family:'Ubuntu Mono';-inkscape-font-specification:'Ubuntu Mono Bold';letter-spacing:0px;word-spacing:0px;fill:#ffffff;fill-opacity:1;stroke:none;stroke-width:1.16429496;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:markers stroke fill"
|
||||
d="m 13.205251,-6.7970011 q 0.368361,0 0.506496,-0.11511 0.149645,-0.1151195 0.149645,-0.2762795 0,-0.4144001 -0.725209,-0.4144001 h -0.425918 v -0.8403301 h 0.425918 q 0.241736,0 0.391383,-0.0921 0.149647,-0.0921 0.149647,-0.28779 0,-0.32231 -0.448939,-0.32231 -0.241738,0 -0.471962,0.0806 -0.230226,0.0806 -0.448941,0.17266 l -0.391382,-0.80578 q 0.253249,-0.16115 0.63312,-0.27626 0.391383,-0.1266202 0.759743,-0.1266202 0.414405,0 0.690677,0.0921 0.28778,0.0921 0.46045,0.2532602 0.172659,0.14964 0.241735,0.36836 0.06909,0.20721 0.06909,0.43744 0,0.2187 -0.103625,0.41439 -0.09207,0.18419 -0.322314,0.3798801 0.333821,0.14965 0.471953,0.4144 0.149648,0.25326 0.149648,0.5640601 0,0.2877795 -0.09208,0.5295095 -0.09207,0.24173 -0.299287,0.42592 -0.207203,0.17268 -0.541028,0.27628 -0.333827,0.10365 -0.817301,0.10365 -0.345337,0 -0.748232,-0.0691 -0.391384,-0.0806 -0.621608,-0.20719 l 0.241736,-0.9093995 q 0.345339,0.1496595 0.587075,0.1956995 0.241736,0.0345 0.529518,0.0345 z" />
|
||||
</g>
|
||||
</svg>
|
After Width: | Height: | Size: 29 KiB |
|
@ -0,0 +1,42 @@
|
|||
#include "mach_gettime.h"
|
||||
#include <mach/mach_time.h>
|
||||
|
||||
#define MT_NANO (+1.0E-9)
|
||||
#define MT_GIGA UINT64_C(1000000000)
|
||||
|
||||
// TODO create a list of timers,
|
||||
static double mt_timebase = 0.0;
|
||||
static uint64_t mt_timestart = 0;
|
||||
|
||||
int clock_gettime(clockid_t clk_id, struct timespec *tp)
|
||||
{
|
||||
kern_return_t retval = KERN_SUCCESS;
|
||||
|
||||
if (clk_id == TIMER_ABSTIME) {
|
||||
if (!mt_timestart) { // only one timer, initialized on the first call to the TIMER
|
||||
mach_timebase_info_data_t tb;
|
||||
mach_timebase_info(&tb);
|
||||
mt_timebase = tb.numer;
|
||||
mt_timebase /= tb.denom;
|
||||
mt_timestart = mach_absolute_time();
|
||||
}
|
||||
|
||||
double diff = (mach_absolute_time() - mt_timestart) * mt_timebase;
|
||||
tp->tv_sec = diff * MT_NANO;
|
||||
tp->tv_nsec = diff - (tp->tv_sec * MT_GIGA);
|
||||
} else { // other clk_ids are mapped to the corresponding mach clock_service
|
||||
clock_serv_t cclock;
|
||||
mach_timespec_t mts;
|
||||
|
||||
host_get_clock_service(mach_host_self(), clk_id, &cclock);
|
||||
retval = clock_get_time(cclock, &mts);
|
||||
mach_port_deallocate(mach_task_self(), cclock);
|
||||
|
||||
tp->tv_sec = mts.tv_sec;
|
||||
tp->tv_nsec = mts.tv_nsec;
|
||||
}
|
||||
|
||||
return retval;
|
||||
}
|
||||
|
||||
/* Copyright (c) 2015-2018 Alf Watt - Open Source - https://opensource.org/licenses/MIT */
|
|
@ -0,0 +1,28 @@
|
|||
#ifndef mach_time_h
|
||||
#define mach_time_h
|
||||
|
||||
#include <sys/types.h>
|
||||
#include <sys/_types/_timespec.h>
|
||||
#include <mach/mach.h>
|
||||
#include <mach/clock.h>
|
||||
|
||||
/* The opengroup spec isn't clear on the mapping from REALTIME to CALENDAR
|
||||
being appropriate or not.
|
||||
http://pubs.opengroup.org/onlinepubs/009695299/basedefs/time.h.html */
|
||||
|
||||
// XXX only supports a single timer
|
||||
#define TIMER_ABSTIME -1
|
||||
#define CLOCK_REALTIME CALENDAR_CLOCK
|
||||
#define CLOCK_MONOTONIC SYSTEM_CLOCK
|
||||
|
||||
typedef int clockid_t;
|
||||
|
||||
/* the mach kernel uses struct mach_timespec, so struct timespec
|
||||
is loaded from <sys/_types/_timespec.h> for compatibility */
|
||||
// struct timespec { time_t tv_sec; long tv_nsec; };
|
||||
|
||||
int clock_gettime(clockid_t clk_id, struct timespec *tp);
|
||||
|
||||
#endif
|
||||
|
||||
/* Copyright (c) 2015-2018 Alf Watt - Open Source - https://opensource.org/licenses/MIT */
|
|
@ -0,0 +1,67 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Statically compile nnn with netbsd-curses, musl-fts and musl libc on Ubuntu
|
||||
#
|
||||
# netbsd-curses: https://github.com/sabotage-linux/netbsd-curses
|
||||
# musl-fts: https://github.com/void-linux/musl-fts
|
||||
# musl libc: https://www.musl-libc.org/
|
||||
#
|
||||
# Dependencies: git
|
||||
#
|
||||
# Usage: musl-static-ubuntu.sh [no_run]
|
||||
# # optional argument - do not to execute the binary after compilation
|
||||
#
|
||||
# Notes:
|
||||
# - run the script within the top-level nnn directory
|
||||
# - installs musl & gits netbsd-curses, musl-fts libs
|
||||
#
|
||||
# Tested on Ubuntu 20.04 x86_64
|
||||
# Author: Arun Prakash Jana
|
||||
|
||||
# Exit on first failure
|
||||
set -e
|
||||
|
||||
# Output binary name
|
||||
BIN=nnn-musl-static
|
||||
|
||||
# Install musl
|
||||
sudo apt install -y --no-install-recommends musl musl-dev musl-tools
|
||||
|
||||
# Get netbsd-curses
|
||||
[ ! -d "./netbsd-curses" ] && git clone https://github.com/sabotage-linux/netbsd-curses
|
||||
|
||||
# Enter the library dir
|
||||
cd netbsd-curses
|
||||
|
||||
# Get the last known working version
|
||||
git checkout v0.3.2
|
||||
|
||||
# Compile the static netbsd-curses libraries
|
||||
if [ ! -d "./libs" ]; then
|
||||
mkdir libs
|
||||
else
|
||||
rm -vf -- libs/*
|
||||
fi
|
||||
make CC=musl-gcc CFLAGS=-O3 LDFLAGS=-static all-static -j$(($(nproc)+1))
|
||||
cp -v libcurses/libcurses.a libterminfo/libterminfo.a libs/
|
||||
|
||||
# Get musl-fts library
|
||||
cd ..
|
||||
[ ! -d "./musl-fts" ] && git clone https://github.com/void-linux/musl-fts --depth=1
|
||||
|
||||
# Compile the static musl-fts library
|
||||
cd musl-fts
|
||||
./bootstrap.sh
|
||||
./configure
|
||||
make CC=musl-gcc CFLAGS=-O3 LDFLAGS=-static -j$(($(nproc)+1))
|
||||
|
||||
# Compile nnn
|
||||
cd ..
|
||||
[ -e "./netbsd-curses" ] || rm -- "$BIN"
|
||||
musl-gcc -O3 -DNORL -DNOMOUSE -std=c11 -Wall -Wextra -Wshadow -I./netbsd-curses/libcurses -I./musl-fts -o "$BIN" src/nnn.c -Wl,-Bsymbolic-functions -lpthread -L./netbsd-curses/libs -lcurses -lterminfo -static -L./musl-fts/.libs -lfts
|
||||
strip "$BIN"
|
||||
|
||||
if [ -z "$1" ]; then
|
||||
# Run the binary with it selected
|
||||
./"$BIN" -d "$BIN"
|
||||
fi
|
|
@ -21,7 +21,7 @@
|
|||
# #############################################################################
|
||||
|
||||
import sys
|
||||
from subprocess import Popen, PIPE, DEVNULL
|
||||
from subprocess import Popen, PIPE
|
||||
|
||||
if len(sys.argv) < 3:
|
||||
print('usage: natool [-a] [-l] [-x] [archive] [file/dir]')
|
||||
|
|
|
@ -1,21 +1,12 @@
|
|||
name: nnn
|
||||
maintainer: Arun Prakash Jana <engineerarun@gmail.com>
|
||||
license: BSD 2-Clause
|
||||
summary: The missing terminal file manager for X.
|
||||
summary: The unorthodox terminal file manager.
|
||||
homepage: https://github.com/jarun/nnn
|
||||
commands:
|
||||
install:
|
||||
- make PREFIX="/usr" strip install DESTDIR="${BP_DESTDIR}"
|
||||
packages:
|
||||
archlinux:
|
||||
builddeps:
|
||||
- make
|
||||
- gcc
|
||||
- pkg-config
|
||||
deps:
|
||||
- ncurses
|
||||
- readline
|
||||
container: "archlinux/base"
|
||||
centos7.5:
|
||||
builddeps:
|
||||
- make
|
||||
|
@ -42,6 +33,19 @@ packages:
|
|||
commands:
|
||||
pre:
|
||||
- yum install epel-release
|
||||
centos7.7:
|
||||
builddeps:
|
||||
- make
|
||||
- gcc
|
||||
- pkgconfig
|
||||
- ncurses-devel
|
||||
- readline-devel
|
||||
deps:
|
||||
- ncurses
|
||||
- readline
|
||||
commands:
|
||||
pre:
|
||||
- yum install epel-release
|
||||
centos8.0:
|
||||
builddeps:
|
||||
- make
|
||||
|
@ -70,12 +74,12 @@ packages:
|
|||
- make
|
||||
- gcc
|
||||
- pkg-config
|
||||
- libncursesw5-dev
|
||||
- libncurses-dev
|
||||
- libreadline-dev
|
||||
deps:
|
||||
- libncursesw5
|
||||
- libncursesw6
|
||||
- readline-common
|
||||
fedora29:
|
||||
fedora32:
|
||||
builddeps:
|
||||
- make
|
||||
- gcc
|
||||
|
@ -85,36 +89,26 @@ packages:
|
|||
deps:
|
||||
- ncurses
|
||||
- readline
|
||||
fedora30:
|
||||
builddeps:
|
||||
- make
|
||||
- gcc
|
||||
- pkg-config
|
||||
- ncurses-devel
|
||||
- readline-devel
|
||||
deps:
|
||||
- ncurses
|
||||
- readline
|
||||
fedora31:
|
||||
builddeps:
|
||||
- make
|
||||
- gcc
|
||||
- pkg-config
|
||||
- ncurses-devel
|
||||
- readline-devel
|
||||
deps:
|
||||
- ncurses
|
||||
- readline
|
||||
opensuse15.1:
|
||||
builddeps:
|
||||
- make
|
||||
- gcc
|
||||
- pkg-config
|
||||
- readline-devel
|
||||
- ncurses-devel
|
||||
deps:
|
||||
- libncurses6
|
||||
- libreadline7
|
||||
# opensuse15.2:
|
||||
# builddeps:
|
||||
# - make
|
||||
# - gcc
|
||||
# - pkg-config
|
||||
# - readline-devel
|
||||
# - ncurses-devel
|
||||
# deps:
|
||||
# - libncurses6
|
||||
# - libreadline7
|
||||
# opensuse.tumbleweed:
|
||||
# builddeps:
|
||||
# - make
|
||||
# - gcc
|
||||
# - pkg-config
|
||||
# - readline-devel
|
||||
# - ncurses-devel
|
||||
# deps:
|
||||
# - libncurses6
|
||||
# - libreadline8
|
||||
ubuntu16.04:
|
||||
builddeps:
|
||||
- make
|
||||
|
@ -135,3 +129,13 @@ packages:
|
|||
deps:
|
||||
- libncursesw5
|
||||
- libreadline7
|
||||
ubuntu20.04:
|
||||
builddeps:
|
||||
- make
|
||||
- gcc
|
||||
- pkg-config
|
||||
- libncurses-dev
|
||||
- libreadline-dev
|
||||
deps:
|
||||
- libncursesw6
|
||||
- libreadline8
|
||||
|
|
|
@ -1,27 +0,0 @@
|
|||
n ()
|
||||
{
|
||||
# Block nesting of nnn in subshells
|
||||
if [ -n $NNNLVL ] && [ "${NNNLVL:-0}" -ge 1 ]; then
|
||||
echo "nnn is already running"
|
||||
return
|
||||
fi
|
||||
|
||||
# The default behaviour is to cd on quit (nnn checks if NNN_TMPFILE is set)
|
||||
# To cd on quit only on ^G, remove the "export" as in:
|
||||
# NNN_TMPFILE="${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.lastd"
|
||||
# NOTE: NNN_TMPFILE is fixed, should not be modified
|
||||
export NNN_TMPFILE="${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.lastd"
|
||||
|
||||
# Unmask ^Q (, ^V etc.) (if required, see `stty -a`) to Quit nnn
|
||||
# stty start undef
|
||||
# stty stop undef
|
||||
# stty lwrap undef
|
||||
# stty lnext undef
|
||||
|
||||
nnn "$@"
|
||||
|
||||
if [ -f "$NNN_TMPFILE" ]; then
|
||||
. "$NNN_TMPFILE"
|
||||
rm -f "$NNN_TMPFILE" > /dev/null
|
||||
fi
|
||||
}
|
|
@ -0,0 +1,30 @@
|
|||
n ()
|
||||
{
|
||||
# Block nesting of nnn in subshells
|
||||
[ "${NNNLVL:-0}" -eq 0 ] || {
|
||||
echo "nnn is already running"
|
||||
return
|
||||
}
|
||||
|
||||
# The behaviour is set to cd on quit (nnn checks if NNN_TMPFILE is set)
|
||||
# If NNN_TMPFILE is set to a custom path, it must be exported for nnn to
|
||||
# see. To cd on quit only on ^G, remove the "export" and make sure not to
|
||||
# use a custom path, i.e. set NNN_TMPFILE *exactly* as follows:
|
||||
# NNN_TMPFILE="${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.lastd"
|
||||
export NNN_TMPFILE="${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.lastd"
|
||||
|
||||
# Unmask ^Q (, ^V etc.) (if required, see `stty -a`) to Quit nnn
|
||||
# stty start undef
|
||||
# stty stop undef
|
||||
# stty lwrap undef
|
||||
# stty lnext undef
|
||||
|
||||
# The command builtin allows one to alias nnn to n, if desired, without
|
||||
# making an infinitely recursive alias
|
||||
command nnn "$@"
|
||||
|
||||
[ ! -f "$NNN_TMPFILE" ] || {
|
||||
. "$NNN_TMPFILE"
|
||||
rm -f -- "$NNN_TMPFILE" > /dev/null
|
||||
}
|
||||
}
|
|
@ -1,8 +1,9 @@
|
|||
# NOTE: set NNN_TMPFILE correctly if you use 'XDG_CONFIG_HOME'
|
||||
|
||||
# The default behaviour is to cd on quit (nnn checks if NNN_TMPFILE is set)
|
||||
# To cd on quit only on ^G, export NNN_TMPFILE after the call to nnn
|
||||
# NOTE: NNN_TMPFILE is fixed, should not be modified
|
||||
# The behaviour is set to cd on quit (nnn checks if NNN_TMPFILE is set)
|
||||
# If NNN_TMPFILE is set to a custom path, it must be exported for nnn to see.
|
||||
# To cd on quit only on ^G, set NNN_TMPFILE after the nnn invocation, and make
|
||||
# sure not to use a custom path.
|
||||
set NNN_TMPFILE=~/.config/nnn/.lastd
|
||||
|
||||
# Unmask ^Q (, ^V etc.) (if required, see `stty -a`) to Quit nnn
|
||||
|
@ -11,4 +12,6 @@ set NNN_TMPFILE=~/.config/nnn/.lastd
|
|||
# stty lwrap undef
|
||||
# stty lnext undef
|
||||
|
||||
alias n 'nnn -fis; source "$NNN_TMPFILE"; rm -f "$NNN_TMPFILE"'
|
||||
# The backslash allows one to alias n to nnn if desired without making an
|
||||
# infinitely recursive alias
|
||||
alias n '\nnn; source "$NNN_TMPFILE"; rm -f -- "$NNN_TMPFILE"'
|
||||
|
|
|
@ -0,0 +1,41 @@
|
|||
# Append this file to ~/.elvish/rc.elv (Elvish > 0.17.0)
|
||||
|
||||
use path
|
||||
|
||||
fn n {|@a|
|
||||
# Block nesting of nnn in subshells
|
||||
if (has-env NNNLVL) {
|
||||
try {
|
||||
if (>= $E:NNNLVL 1) {
|
||||
echo "nnn is already running"
|
||||
return
|
||||
}
|
||||
} catch e {
|
||||
nop
|
||||
}
|
||||
}
|
||||
|
||||
# The behaviour is set to cd on quit (nnn checks if NNN_TMPFILE is set)
|
||||
# If NNN_TMPFILE is set to a custom path, it must be exported for nnn to
|
||||
# see.
|
||||
if (has-env XDG_CONFIG_HOME) {
|
||||
set-env NNN_TMPFILE $E:XDG_CONFIG_HOME/nnn/.lastd
|
||||
} else {
|
||||
set-env NNN_TMPFILE $E:HOME/.config/nnn/.lastd
|
||||
}
|
||||
|
||||
# Unmask ^Q (, ^V etc.) (if required, see `stty -a`) to Quit nnn
|
||||
# stty start undef
|
||||
# stty stop undef
|
||||
# stty lwrap undef
|
||||
# stty lnext undef
|
||||
|
||||
# The e: prefix allows one to alias n to nnn if desired without making an
|
||||
# infinitely recursive alias
|
||||
e:nnn $@a
|
||||
|
||||
if (path:is-regular $E:NNN_TMPFILE) {
|
||||
eval (slurp < $E:NNN_TMPFILE)
|
||||
rm -- $E:NNN_TMPFILE
|
||||
}
|
||||
}
|
|
@ -2,19 +2,17 @@
|
|||
# e.g. ~/.config/fish/functions/n.fish
|
||||
# or, add the lines to the 'config.fish' file.
|
||||
|
||||
function n --description 'support nnn quit and change directory'
|
||||
function n --wraps nnn --description 'support nnn quit and change directory'
|
||||
# Block nesting of nnn in subshells
|
||||
if test -n NNNLVL
|
||||
if [ (expr $NNNLVL + 0) -ge 1 ]
|
||||
echo "nnn is already running"
|
||||
return
|
||||
end
|
||||
if test -n "$NNNLVL" -a "$NNNLVL" -ge 1
|
||||
echo "nnn is already running"
|
||||
return
|
||||
end
|
||||
|
||||
# The default behaviour is to cd on quit (nnn checks if NNN_TMPFILE is set)
|
||||
# To cd on quit only on ^G, remove the "-x" as in:
|
||||
# set NNN_TMPFILE "$XDG_CONFIG_HOME/nnn/.lastd"
|
||||
# NOTE: NNN_TMPFILE is fixed, should not be modified
|
||||
# The behaviour is set to cd on quit (nnn checks if NNN_TMPFILE is set)
|
||||
# If NNN_TMPFILE is set to a custom path, it must be exported for nnn to
|
||||
# see. To cd on quit only on ^G, remove the "-x" from both lines below,
|
||||
# without changing the paths.
|
||||
if test -n "$XDG_CONFIG_HOME"
|
||||
set -x NNN_TMPFILE "$XDG_CONFIG_HOME/nnn/.lastd"
|
||||
else
|
||||
|
@ -27,10 +25,12 @@ function n --description 'support nnn quit and change directory'
|
|||
# stty lwrap undef
|
||||
# stty lnext undef
|
||||
|
||||
nnn $argv
|
||||
# The command function allows one to alias this function to `nnn` without
|
||||
# making an infinitely recursive alias
|
||||
command nnn $argv
|
||||
|
||||
if test -e $NNN_TMPFILE
|
||||
source $NNN_TMPFILE
|
||||
rm $NNN_TMPFILE
|
||||
rm -- $NNN_TMPFILE
|
||||
end
|
||||
end
|
||||
|
|
|
@ -0,0 +1,37 @@
|
|||
# Run nnn with dynamic changing directory to the environment.
|
||||
#
|
||||
# $env.XDG_CONFIG_HOME sets the home folder for `nnn` folder and its $env.NNN_TMPFILE variable.
|
||||
# See manual NNN(1) for more information.
|
||||
#
|
||||
# Import module using `use quitcd.nu n` to have `n` command in your context.
|
||||
export def --env n [
|
||||
...args : string # Extra flags to launch nnn with.
|
||||
--selective = false # Change directory only when exiting via ^G.
|
||||
] -> nothing {
|
||||
|
||||
# The behaviour is set to cd on quit (nnn checks if $env.NNN_TMPFILE is set).
|
||||
# Hard-coded to its respective behaviour in `nnn` source-code.
|
||||
let nnn_tmpfile = $env
|
||||
| default '~/.config/' 'XDG_CONFIG_HOME'
|
||||
| get 'XDG_CONFIG_HOME'
|
||||
| path join 'nnn/.lastd'
|
||||
| path expand
|
||||
|
||||
# Launch nnn. Add desired flags after `^nnn`, ex: `^nnn -eda ...$args`,
|
||||
# or make an alias `alias n = n -eda`.
|
||||
if $selective {
|
||||
^nnn ...$args
|
||||
} else {
|
||||
NNN_TMPFILE=$nnn_tmpfile ^nnn ...$args
|
||||
}
|
||||
|
||||
if ($nnn_tmpfile | path exists) {
|
||||
# Remove <cd '> from the first part of the string and the last single quote <'>.
|
||||
# Fix post-processing of nnn's given path that escapes its single quotes with POSIX syntax.
|
||||
let path = open $nnn_tmpfile | str substring 4..-1 | str replace --all `'\''` `'`
|
||||
|
||||
^rm -- $nnn_tmpfile
|
||||
|
||||
cd $path
|
||||
}
|
||||
}
|
|
@ -1,27 +0,0 @@
|
|||
n ()
|
||||
{
|
||||
# Block nesting of nnn in subshells
|
||||
if [ -n $NNNLVL ] && [ "${NNNLVL:-0}" -ge 1 ]; then
|
||||
echo "nnn is already running"
|
||||
return
|
||||
fi
|
||||
|
||||
# The default behaviour is to cd on quit (nnn checks if NNN_TMPFILE is set)
|
||||
# To cd on quit only on ^G, remove the "export" as in:
|
||||
# NNN_TMPFILE="${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.lastd"
|
||||
# NOTE: NNN_TMPFILE is fixed, should not be modified
|
||||
export NNN_TMPFILE="${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.lastd"
|
||||
|
||||
# Unmask ^Q (, ^V etc.) (if required, see `stty -a`) to Quit nnn
|
||||
# stty start undef
|
||||
# stty stop undef
|
||||
# stty lwrap undef
|
||||
# stty lnext undef
|
||||
|
||||
nnn "$@"
|
||||
|
||||
if [ -f "$NNN_TMPFILE" ]; then
|
||||
. "$NNN_TMPFILE"
|
||||
rm -f "$NNN_TMPFILE" > /dev/null
|
||||
fi
|
||||
}
|
|
@ -0,0 +1,37 @@
|
|||
#!/bin/sh
|
||||
#
|
||||
# Usage: ./misc/test/benchmark.sh ./nnn /tmp/testdir1 ./testdir2 ...
|
||||
#
|
||||
# Don't forget to build nnn in benchmark mode: make O_BENCH=1
|
||||
|
||||
# Use a test dir filled with genfiles.sh to get interesting output
|
||||
# (or maybe /usr/lib/)
|
||||
|
||||
LANG=C
|
||||
|
||||
TIME_VAL=${TIME_VAL:-"real"}
|
||||
|
||||
SAMPLES=${SAMPLES:-100}
|
||||
|
||||
EXE=$1
|
||||
|
||||
bench_val () {
|
||||
(time "$1" "$2") 2>&1 |\
|
||||
awk '$1=="'"$TIME_VAL"'"{match($2, /[0-9]*\.[0-9]*/) ; print substr($2, RSTART, RLENGTH)}'
|
||||
}
|
||||
|
||||
bench_dir () {
|
||||
i=$SAMPLES
|
||||
printf "$2"
|
||||
while [ $((i--)) -gt 0 ] ; do
|
||||
printf "\t%s" "$(bench_val "$1" "$2")"
|
||||
done
|
||||
printf "\n"
|
||||
}
|
||||
|
||||
shift
|
||||
|
||||
for dir in "$@" ; do
|
||||
bench_dir "$EXE" "$dir"
|
||||
done
|
||||
|
|
@ -0,0 +1,8 @@
|
|||
#!/bin/sh
|
||||
|
||||
# Generates 100000 files in the current directory
|
||||
|
||||
i=1; while [ $i -le 100000 ]; do
|
||||
mktemp -p . -t 'XXXXXXXXXXXXXXXXXXXXX'
|
||||
i=$(( i + 1 ))
|
||||
done
|
|
@ -0,0 +1,20 @@
|
|||
#!/usr/bin/env python3
|
||||
#
|
||||
# Usage: ./plot-bench.py datafile
|
||||
# (where datafile is the output of benchmark.sh)
|
||||
|
||||
import matplotlib.pyplot as plt
|
||||
import sys
|
||||
|
||||
def bench_file_to_lists(infile):
|
||||
return [[float(entry) for entry in line.split('\t')[1:]] for line in infile.readlines()]
|
||||
|
||||
def plot_data(data):
|
||||
fig = plt.figure()
|
||||
ax = fig.add_axes([0,0,1,1])
|
||||
ax.violinplot(data)
|
||||
plt.savefig("plot.svg")
|
||||
|
||||
filename = sys.argv[1]
|
||||
|
||||
plot_data(bench_file_to_lists(open(filename)))
|
609
nnn.1
609
nnn.1
|
@ -1,48 +1,56 @@
|
|||
.Dd Jan 15, 2020
|
||||
.Dd Aug 27, 2023
|
||||
.Dt NNN 1
|
||||
.Os
|
||||
.Sh NAME
|
||||
.Nm nnn
|
||||
.Nd the missing terminal file manager for X
|
||||
.Nd The unorthodox terminal file manager.
|
||||
.Sh SYNOPSIS
|
||||
.Nm
|
||||
.Op Ar -a
|
||||
.Op Ar -A
|
||||
.Op Ar -aAcCdDeEfgHJKnQrRSuUVxh
|
||||
.Op Ar -b key
|
||||
.Op Ar -c
|
||||
.Op Ar -d
|
||||
.Op Ar -E
|
||||
.Op Ar -g
|
||||
.Op Ar -H
|
||||
.Op Ar -K
|
||||
.Op Ar -n
|
||||
.Op Ar -F val
|
||||
.Op Ar -l val
|
||||
.Op Ar -p file
|
||||
.Op Ar -Q
|
||||
.Op Ar -r
|
||||
.Op Ar -R
|
||||
.Op Ar -P key
|
||||
.Op Ar -s name
|
||||
.Op Ar -S
|
||||
.Op Ar -v
|
||||
.Op Ar -V
|
||||
.Op Ar -x
|
||||
.Op Ar -h
|
||||
.Op Ar -t secs
|
||||
.Op Ar -T key
|
||||
.Op Ar PATH
|
||||
.Sh DESCRIPTION
|
||||
.Nm
|
||||
(Nnn's Not Noice) is a performance-optimized, feature-packed fork of
|
||||
noice (http://git.2f30.org/noice/) with seamless desktop integration,
|
||||
simplified navigation, \fInavigate-as-you-type\fR mode with auto select,
|
||||
disk usage analyzer mode, bookmarks, contexts, application launcher,
|
||||
familiar navigation shortcuts, subshell spawning and much more.It
|
||||
remains a simple and efficient file manager that stays out of your way.
|
||||
.Pq Nnn's Not Noice
|
||||
is a performance-optimized, feature-packed fork of noice
|
||||
.Em http://git.2f30.org/noice/
|
||||
with seamless desktop integration, simplified navigation,
|
||||
.Em type-to-nav
|
||||
mode with dir auto-enter, disk usage analyzer mode, bookmarks,
|
||||
contexts, application launcher, familiar navigation shortcuts,
|
||||
subshell spawning and much more. It remains a simple and
|
||||
efficient file manager that stays out of your way.
|
||||
.Pp
|
||||
.Nm
|
||||
opens the current working directory by default if
|
||||
opens the current working directory if
|
||||
.Ar PATH
|
||||
is not specified.
|
||||
is not specified. If
|
||||
.Ar PATH
|
||||
is specified and it exists,
|
||||
.Nm
|
||||
will open it. If the
|
||||
.Ar PATH
|
||||
doesn't exist and ends with a \fB/\fR,
|
||||
.Nm
|
||||
will attempt to create the directory tree and open it. Otherwise,
|
||||
.Ar PATH
|
||||
is considered a path to a regular file and
|
||||
.Nm
|
||||
attempts to create the complete directory tree to the file, open
|
||||
the parent directory and prompt to create the new file in it with
|
||||
the base filename.
|
||||
.Sh KEYBINDS
|
||||
.Pp
|
||||
Press \fB?\fR in
|
||||
Press
|
||||
.Ql \&?
|
||||
in
|
||||
.Nm
|
||||
to see the list of keybinds.
|
||||
.Sh OPTIONS
|
||||
|
@ -51,34 +59,63 @@ to see the list of keybinds.
|
|||
supports the following options:
|
||||
.Pp
|
||||
.Fl a
|
||||
use access time for all operations (default: modification time)
|
||||
auto-setup temporary \fBNNN_FIFO\fR (described in \fIENVIRONMENT\fR section)
|
||||
.Pp
|
||||
.Fl A
|
||||
disable directory auto-select in navigate-as-you-type mode
|
||||
disable directory auto-enter on unique filter match
|
||||
.Pp
|
||||
.Fl "b key"
|
||||
specify bookmark key to open
|
||||
.Pp
|
||||
.Fl B
|
||||
use bsdtar for archives (default: atool)
|
||||
.Pp
|
||||
.Fl c
|
||||
opener opens files in cli utilities only
|
||||
indicates that the opener is a cli-only opener (overrides -e)
|
||||
.Pp
|
||||
.Fl C
|
||||
8-color scheme - color directories by context, disable file colors
|
||||
.Pp
|
||||
.Fl d
|
||||
detail mode
|
||||
.Pp
|
||||
.Fl D
|
||||
show directories in context color with \fBNNN_FCOLORS\fR set
|
||||
.Pp
|
||||
.Fl e
|
||||
open text files in $VISUAL (else $EDITOR, fallback vi) [preferably CLI]
|
||||
.Pp
|
||||
.Fl E
|
||||
use $EDITOR for internal undetached edits
|
||||
.Pp
|
||||
.Fl f
|
||||
use readline history file
|
||||
.Pp
|
||||
.Fl "F val"
|
||||
fifo notification mode
|
||||
0: notify as previewer, 1: notify as explorer
|
||||
.Pp
|
||||
.Fl g
|
||||
use regex filters instead of substring match
|
||||
.Pp
|
||||
.Fl H
|
||||
show hidden files
|
||||
.Pp
|
||||
.Fl i
|
||||
show current file information in info bar (may be slow)
|
||||
.Pp
|
||||
.Fl J
|
||||
disable auto-advance on selection
|
||||
(eg. selecting an entry will no longer move cursor to the next entry)
|
||||
.Pp
|
||||
.Fl K
|
||||
test for keybind collision
|
||||
test for keybind collision and exit
|
||||
.Pp
|
||||
.Fl "l val"
|
||||
number of lines to move per mouse wheel scroll
|
||||
.Pp
|
||||
.Fl n
|
||||
start in navigate-as-you-type mode
|
||||
start in type-to-nav mode
|
||||
.Pp
|
||||
.Fl o
|
||||
open files only on Enter key
|
||||
|
@ -86,38 +123,54 @@ supports the following options:
|
|||
.Fl "p file"
|
||||
copy (or \fIpick\fR) selection to file, or stdout if file='-'
|
||||
.Pp
|
||||
.Fl "P key"
|
||||
specify plugin key to run
|
||||
.Pp
|
||||
.Fl Q
|
||||
disable confirmation on quit with multiple contexts active
|
||||
.Pp
|
||||
.Fl r
|
||||
show cp, mv progress
|
||||
(Linux-only, needs advcpmv; '^T' shows the progress on BSD/macOS)
|
||||
(Linux-only, needs \fIadvcpmv\fR; '^T' shows the progress on BSD/macOS)
|
||||
.Pp
|
||||
.Fl R
|
||||
disable rollover at edges
|
||||
disable rollover at edges (eg. pressing \fIdown\fR while on the last
|
||||
entry will no longer move cursor to the first entry and vice\-versa)
|
||||
.Pp
|
||||
.Fl "s name"
|
||||
load a session by name
|
||||
.Pp
|
||||
.Fl S
|
||||
start in disk usage analyzer mode
|
||||
persistent session
|
||||
.Pp
|
||||
.Fl v
|
||||
use case-insensitive version compare to sort files
|
||||
.Fl "t secs"
|
||||
idle timeout in seconds to lock terminal
|
||||
.Pp
|
||||
.Fl "T key"
|
||||
sort order
|
||||
keys: 'a'pparent disk usage / 'd'isk usage / 'e'xtension / 'r'everse / 's'ize / 't'ime / 'v'ersion
|
||||
capitalize to reverse (except 'r')
|
||||
.Pp
|
||||
.Fl u
|
||||
use selection if available, don't prompt to choose between selection and hovered entry
|
||||
.Pp
|
||||
.Fl U
|
||||
show user and group names in status bar
|
||||
.Pp
|
||||
.Fl V
|
||||
show version and exit
|
||||
.Pp
|
||||
.Fl x
|
||||
show notis on selection cp, mv, rm completion
|
||||
copy path to system clipboard on select
|
||||
show notifications on selection cp, mv, rm completion (requires \fI.ntfy\fR plugin)
|
||||
copy path to system clipboard on selection (requires \fI.cbcp\fR plugin)
|
||||
show xterm title (if non-picker mode)
|
||||
.Pp
|
||||
.Fl h
|
||||
show program help and exit
|
||||
.Sh CONFIGURATION
|
||||
There is no configuration file. Associated files are at
|
||||
.Pp
|
||||
\fB${XDG_CONFIG_HOME:-$HOME/.config}/nnn/\fR
|
||||
.Pa ${XDG_CONFIG_HOME:-$HOME/.config}/nnn/
|
||||
.Pp
|
||||
Configuration is done using a few optional (set if you need) environment
|
||||
variables. See ENVIRONMENT section.
|
||||
|
@ -127,8 +180,7 @@ uses \fIxdg-open\fR (on Linux), \fIopen(1)\fR (on macOS), \fIcygstart\fR on
|
|||
(Cygwin) and \fIopen\fR on (Haiku) as the desktop opener. It's also possible
|
||||
to specify a custom opener. See ENVIRONMENT section.
|
||||
.Sh CONTEXTS
|
||||
Contexts serve the purpose of exploring multiple directories simultaneously. 4
|
||||
contexts are available. The status of the contexts are shown in the top left
|
||||
Open multiple locations with 4 contexts. The status is shown in the top left
|
||||
corner:
|
||||
.Pp
|
||||
- the current context is in reverse video
|
||||
|
@ -137,56 +189,65 @@ corner:
|
|||
.br
|
||||
- rest are inactive
|
||||
.Pp
|
||||
On context creation, the state of the previous context is copied. Each context
|
||||
remembers its last visited directory.
|
||||
.Pp
|
||||
Each context can have its own directory color specified. See ENVIRONMENT
|
||||
section.
|
||||
A new context copies the state of the previous context. Each context can have
|
||||
its own color. See ENVIRONMENT section.
|
||||
.Sh SESSIONS
|
||||
Sessions are a way to save and restore states of work. A session stores the
|
||||
settings and contexts.
|
||||
settings and contexts. Sessions can be loaded at runtime or with a program
|
||||
option.
|
||||
.Pp
|
||||
Sessions can be loaded dynamically from within a running
|
||||
.Nm
|
||||
instance, or with a program option.
|
||||
.Pp
|
||||
When a session is loaded dynamically, the last working session is saved
|
||||
automatically to a dedicated -- "last session" -- session file.
|
||||
- When a session is loaded at runtime, the last working state is saved
|
||||
automatically to a dedicated "auto session" session file. Session option
|
||||
\fIrestore\fR would restore the "auto session".
|
||||
.br
|
||||
- The persistent session option is global. If it is used, the last active session
|
||||
will be updated with the final state at program quit.
|
||||
.br
|
||||
- The "auto session" is used in persistent session mode if no session is active.
|
||||
.br
|
||||
- Listing input stream and opening a bookmark by key have a higher priority to
|
||||
session options (-s/-S).
|
||||
.Pp
|
||||
All the session files are located by session name in the directory
|
||||
.Pp
|
||||
\fB${XDG_CONFIG_HOME:-$HOME/.config}/nnn/sessions\fR
|
||||
.Pp
|
||||
"@" is the "last session" file.
|
||||
"@" is the "auto session" file.
|
||||
.Sh FILTERS
|
||||
Filters are strings to find matching entries in the current directory
|
||||
instantly (\fIsearch-as-you-type\fR). There is a program option to switch to
|
||||
regex filters. Matches are case-insensitive by default. In each context the
|
||||
last filter is persisted at runtime or in saved sessions.
|
||||
Filters are strings (or regex patterns) to find matching entries in the current
|
||||
directory instantly (\fIsearch-as-you-type\fR). Matches are case-insensitive by
|
||||
default. The last filter in each context is persisted at runtime or in saved
|
||||
sessions.
|
||||
.br
|
||||
When there's a unique match and it's a directory,
|
||||
.Nm
|
||||
auto enters the directory. Use the relevant program option to disable this.
|
||||
.Pp
|
||||
Special keys at empty filter prompt:
|
||||
Special keys at filter prompt:
|
||||
.Bd -literal
|
||||
-------- + ---------------------------------------
|
||||
Key | Function
|
||||
-------- + ---------------------------------------
|
||||
^char | Usual keybind functionality
|
||||
Esc | Exit filter prompt but skip dir refresh
|
||||
Alt+Esc | Unfilter, quit context
|
||||
-------- + ---------------------------------------
|
||||
.Ed
|
||||
.Pp
|
||||
- toggle between string and regex: '/'
|
||||
.br
|
||||
- toggle case sensitivity: ':'
|
||||
.br
|
||||
- apply the last filter (or clear filter if non-empty): '^L'
|
||||
.br
|
||||
- show help and config screen: '?'
|
||||
.br
|
||||
- show command prompt: ']'
|
||||
.br
|
||||
- launch an application: '='
|
||||
.br
|
||||
- run a plugin by its key: ';'
|
||||
.br
|
||||
- pin current directory: ','
|
||||
.Pp
|
||||
Other noteworthy keys:
|
||||
.Pp
|
||||
- '^char': usual keybind functionality
|
||||
.br
|
||||
- 'Esc': exit filter prompt but skip dir refresh
|
||||
Special keys at \fBempty filter prompt\fR:
|
||||
.Bd -literal
|
||||
------ + ---------------------------------------
|
||||
Key | Function
|
||||
------ + ---------------------------------------
|
||||
? | Show help and config screen
|
||||
/ | Toggle between string and regex
|
||||
: | Toggle case-sensitivity
|
||||
^L | Clear filter (\fIif prompt is non-empty\fR)
|
||||
| OR apply last filter
|
||||
Bksp | Stay at filter prompt and refresh dir
|
||||
Del | Stay at filter prompt and refresh dir
|
||||
------ + ---------------------------------------
|
||||
.Ed
|
||||
.Pp
|
||||
Common regex use cases:
|
||||
.Pp
|
||||
|
@ -196,142 +257,360 @@ Common regex use cases:
|
|||
(2) Type '\\.mkv' to list all MKV files.
|
||||
.br
|
||||
(3) Use '.*' to match any character (\fIsort of\fR fuzzy search).
|
||||
.Pp
|
||||
In the \fInavigate-as-you-type\fR mode directories are opened in filter mode,
|
||||
allowing continuous navigation. Works best with the \fBarrow keys\fR.
|
||||
.br
|
||||
When there's a unique match and it's a directory,
|
||||
.Nm
|
||||
auto selects the directory and enters it in this mode. Use the relevant
|
||||
program option to disable this behaviour.
|
||||
(4) Exclude filenames having 'nnn' (compiled with PCRE lib): '^(?!nnn)'
|
||||
.Pp
|
||||
In the \fBtype-to-nav\fR mode directories are opened in filter
|
||||
mode, allowing continuous navigation.
|
||||
.Pp
|
||||
Additional special keys at \fBempty filter prompt\fR
|
||||
in \fBtype-to-nav\fR mode:
|
||||
.Bd -literal
|
||||
------ + ------------------------
|
||||
Key | Function
|
||||
------ + ------------------------
|
||||
' | Go to first non-dir file
|
||||
+ | Toggle file selection
|
||||
, | Mark CWD
|
||||
- | Go to last visited dir
|
||||
. | Show hidden files
|
||||
; | Run a plugin by its key
|
||||
= | Launch a GUI application
|
||||
> | Export file list
|
||||
@ | Visit start dir
|
||||
] | Show command prompt
|
||||
` | Visit /
|
||||
~ | Go HOME
|
||||
------ + ------------------------
|
||||
.Ed
|
||||
.Sh SELECTION
|
||||
.Nm
|
||||
allows file selection across directories and contexts!
|
||||
.Pp
|
||||
There are 3 groups of keybinds to add files to selection:
|
||||
.Pp
|
||||
(1) hovered file selection toggle (deselects if '+' is visible before the
|
||||
entry, else adds to selection)
|
||||
(1) hovered file selection toggle
|
||||
- deselects if '+' is visible before the entry, else adds to selection
|
||||
.br
|
||||
(2) add a range of files to selection (repeat the range key on the same entry
|
||||
twice to clear selection completely)
|
||||
(2) add a range of files to selection
|
||||
- repeat the range key on the same entry twice to clear selection completely
|
||||
.br
|
||||
(3) add all files in the current directory to selection
|
||||
.Pp
|
||||
A selection can be edited, copied, moved, removed, archived or linked.
|
||||
.Pp
|
||||
Absolute paths of the selected files are copied to \fB.selection\fR file in
|
||||
the config directory.
|
||||
the config directory. The selection file is shared between multiple program
|
||||
instances. Selection from multiple instances are not merged. The last instance
|
||||
writing to the file overwrites earlier contents. If you have 2 instances of
|
||||
.Nm
|
||||
\fIopen\fR in 2 panes of a terminal multiplexer, you can select in one pane and
|
||||
use the selection in the other pane. The selection gets cleared in the
|
||||
.Nm
|
||||
instance where the selection was made on mv/rm (but not on cp).
|
||||
.Pp
|
||||
To edit the selection use the _edit selection_ key. Use this key to remove a
|
||||
file from selection after you navigate away from its directory. Editing doesn't
|
||||
end the selection mode. You can add more files to the selection and edit the
|
||||
list again. If no file is selected in the current session, this option attempts
|
||||
.Nm
|
||||
clears the selection after a successful operation with the selection. Plugins
|
||||
are allowed to define the behaviour individually.
|
||||
.Pp
|
||||
To edit the selection use the _edit selection_ key. Editing doesn't end the
|
||||
selection mode. You can add more files to the selection and edit the list
|
||||
again. If no file is selected in the current session, this option attempts
|
||||
to list the selection file.
|
||||
.Pp
|
||||
.Nm
|
||||
can show the total size of non-filtered selected files listed in a
|
||||
directory. For directories, only the size of the directory is added by
|
||||
default. To add the size of the contents of a directory, switch to du mode.
|
||||
.Sh FIND AND LIST
|
||||
There are two ways to search and list:
|
||||
.Pp
|
||||
- feed a list of file paths as input
|
||||
.br
|
||||
- search using a plugin (e.g. \fIfinder\fR) and list the results
|
||||
.Pp
|
||||
File paths must be NUL-separated ('\\0'). Paths and can be relative to the
|
||||
current directory or absolute. Invalid paths in the input are ignored. Input
|
||||
processing limit is 16,384 paths or 64 MiB (max_paths x max_path_len) of data.
|
||||
.Pp
|
||||
To list the input stream, start
|
||||
.Nm
|
||||
by writing to its standard input. E.g., to list files in current
|
||||
directory larger than
|
||||
1M:
|
||||
.Bd -literal
|
||||
find -maxdepth 1 -size +1M -print0 | nnn
|
||||
.Ed
|
||||
.Pp
|
||||
or redirect a list from a file:
|
||||
.Bd -literal
|
||||
nnn < files.txt
|
||||
.Ed
|
||||
.Pp
|
||||
Handy bash/zsh shell function to list files by mime-type in current directory:
|
||||
.Bd -literal
|
||||
# to show video files, run: list video
|
||||
|
||||
list ()
|
||||
{
|
||||
find . -maxdepth 1 | file -if- | grep "$1" | awk -F: '{printf "%s%c", $1, 0}' | nnn
|
||||
}
|
||||
.Ed
|
||||
.Pp
|
||||
A temporary directory will be created containing symlinks to the given
|
||||
paths. Any action performed on these symlinks will be performed only on their
|
||||
targets, after which they might become invalid.
|
||||
.Pp
|
||||
Right arrow or 'l' on a symlink in the listing dir takes to the target
|
||||
file. Press '-' to return to the listing dir. Press 'Enter' to open the symlink.
|
||||
.Pp
|
||||
Listing input stream can be scripted. It can be extended to pick (option -p)
|
||||
selected entries from the listed results.
|
||||
.Sh BOOKMARKS
|
||||
There are 2 ways (can be used together) to manage bookmarks.
|
||||
.Pp
|
||||
(1) Bookmark keys: See \fBNNN_BMS\fR under \fIENVIORNMENT\fR section on how to set
|
||||
bookmark keys.
|
||||
|
||||
The select bookmark key \fIb\fR lists all the bookmark keys set in \fBNNN_BMS\fR
|
||||
in the bookmarks prompt.
|
||||
.Pp
|
||||
(2) Symlinked bookmarks: A symlinked bookmark to the current directory can
|
||||
be created with the \fIB\fR key (or manually under ~/.config/nnn/bookmarks).
|
||||
|
||||
Pressing 'Enter' at the bookmarks prompt takes to this directory.
|
||||
If \fBNNN_BMS\fR is not set, the select bookmark key directly opens it.
|
||||
.Pp
|
||||
On entering a bookmark, the directory where the select bookmark key was
|
||||
pressed is set as the previous directory. Press '-' to return to it.
|
||||
.Pp
|
||||
.Sh UNITS
|
||||
The minimum file size unit is byte (B). The rest are K, M, G, T, P, E, Z, Y
|
||||
(powers of 1024), same as the default units in \fIls\fR.
|
||||
.Sh ENVIRONMENT
|
||||
The SHELL, EDITOR (VISUAL, if defined) and PAGER environment variables take
|
||||
precedence when dealing with the !, e and p commands respectively. A single
|
||||
combination to arguments is supported for SHELL and PAGER.
|
||||
The SHELL, VISUAL (else EDITOR) and PAGER environment variables are
|
||||
used. A single combination of arguments is supported for SHELL and PAGER.
|
||||
.Pp
|
||||
\fBNNN_OPTS:\fR binary options to
|
||||
.Nm
|
||||
.Bd -literal
|
||||
export NNN_OPTS="cEnrx"
|
||||
.Ed
|
||||
.Pp
|
||||
\fBNNN_OPENER:\fR specify a custom file opener.
|
||||
.Bd -literal
|
||||
export NNN_OPENER=nuke
|
||||
|
||||
NOTE: `nuke` is a file opener available in plugin repository
|
||||
NOTE: 'nuke' is a file opener available in the plugin repository.
|
||||
.Ed
|
||||
.Pp
|
||||
\fBNNN_BMS:\fR bookmark string as \fIkey_char:location\fR pairs
|
||||
(max 10) separated by \fI;\fR:
|
||||
separated by \fI;\fR:
|
||||
.Bd -literal
|
||||
export NNN_BMS='d:~/Documents;u:/home/user/Cam Uploads;D:~/Downloads/'
|
||||
|
||||
NOTE: To go to a bookmark, press the Lead key followed by the bookmark key.
|
||||
export NNN_BMS="d:$HOME/Docs;u:/home/user/Cam Uploads;D:$HOME/Downloads/"
|
||||
.Ed
|
||||
.Pp
|
||||
\fBNNN_PLUG:\fR directly executable plugins as \fIkey_char:location\fR pairs
|
||||
(max 15) separated by \fI;\fR:
|
||||
These bookmarks are listed in the help and config screen (key ?).
|
||||
.Pp
|
||||
\fBNNN_PLUG:\fR directly executable plugins as \fIkey_char:plugin\fR pairs
|
||||
separated by \fI;\fR:
|
||||
.Bd -literal
|
||||
export NNN_PLUG='o:fzopen;p:mocplay;d:diffs;m:nmount;t:imgthumb'
|
||||
export NNN_PLUG='f:finder;o:fzopen;p:mocplay;d:diffs;t:nmount;v:imgview'
|
||||
|
||||
NOTES:
|
||||
1. To run a plugin directly, press \fI;\fR followed by the plugin key
|
||||
2. To skip directory refresh after running a plugin,prefix with \fB-\fR
|
||||
1. To run a plugin directly, press \fI;\fR followed by the key.
|
||||
2. Alternatively, combine with \fIAlt\fR (i.e. \fIAlt+key\fR).
|
||||
3. To skip directory refresh after running a plugin, prefix with \fB-\fR.
|
||||
|
||||
export NNN_PLUG='m:-mediainfo'
|
||||
export NNN_PLUG='p:-plugin'
|
||||
.Ed
|
||||
.Pp
|
||||
To assign keys to arbitrary non-background non-shell-interpreted cli
|
||||
commands and invoke like plugins, add \fI_\fR (underscore) before the
|
||||
command.
|
||||
To assign keys to arbitrary non-background cli commands and invoke like
|
||||
plugins, add \fB!\fR before the command.
|
||||
.Bd -literal
|
||||
export NNN_PLUG='x:_chmod +x $nnn;g:_git log;s:_smplayer $nnn;o:fzopen'
|
||||
export NNN_PLUG='x:!chmod +x "$nnn";g:!git log;s:!smplayer "$nnn"'
|
||||
|
||||
To pick and run an unassigned plugin, press \fBEnter\fR at the plugin prompt.
|
||||
To run a plugin at startup, use the option `-P` followed by the plugin key.
|
||||
|
||||
NOTES:
|
||||
1. Use single quotes for $NNN_PLUG so $nnn is not interpreted
|
||||
2. $nnn should be the last argument (IF used)
|
||||
3. (Again) add \fB_\fR before the command
|
||||
1. Place $nnn (or exported variables) in double quotes (\fB"$nnn"\fR)
|
||||
2. Use single quotes for $NNN_PLUG so "$nnn" is not interpreted
|
||||
3. (Again) add \fB!\fR before the command
|
||||
4. To disable directory refresh after running a \fIcommand as plugin\fR,
|
||||
prefix with \fB-_\fR
|
||||
prefix with \fB-!\fR
|
||||
5. To skip user confirmation after command execution, suffix with \fB*\fR
|
||||
Note: Do not use \fB*\fR with programs those run and exit e.g. cat
|
||||
|
||||
export NNN_PLUG='y:-_sync*'
|
||||
export NNN_PLUG='y:-!sync*'
|
||||
|
||||
6. To run a \fIGUI app as plugin\fR, add a \fB&\fR after \fB!\fR.
|
||||
|
||||
export NNN_PLUG='m:-!&mousepad "$nnn"'
|
||||
|
||||
7. To show the output of run-and-exit commands which do not need user input,
|
||||
add \fB|\fR (pipe) after \fB!\fR
|
||||
Note: This option is incompatible with \fB&\fR (terminal output is masked
|
||||
for GUI programs) and ignores \fB*\fR (output is already paged for user).
|
||||
|
||||
export NNN_PLUG='m:-!|mediainfo "$nnn";t:-!|tree -ps;l:-!|ls -lah --group-directories-first'
|
||||
|
||||
EXAMPLES:
|
||||
----------------------------------- + -------------------------------------------------
|
||||
Key:Command | Description
|
||||
----------------------------------- + -------------------------------------------------
|
||||
e:-_vi $nnn* | Edit hovered file in vi
|
||||
k:-_fuser -kiv $nnn* | Interactively kill process(es) using hovered file
|
||||
l:_git log | Show git log
|
||||
n:-_vi /home/user/Dropbox/dir/note* | Take quick notes in a synced file/dir of notes
|
||||
p:-_less -iR $nnn* | Page through hovered file in less
|
||||
s:_smplayer -minigui $nnn* | Play hovered media file, even unfinished download
|
||||
x:_chmod +x $nnn | Make the hovered file executable
|
||||
y:-_sync* | Flush cached writes
|
||||
----------------------------------- + -------------------------------------------------
|
||||
.Ed
|
||||
.Pp
|
||||
\fBNNN_USE_EDITOR:\fR use VISUAL (else EDITOR, preferably CLI, fallback vi)
|
||||
to handle text files.
|
||||
.Bd -literal
|
||||
export NNN_USE_EDITOR=1
|
||||
.Ed
|
||||
.Pp
|
||||
\fBNNN_CONTEXT_COLORS:\fR string of color codes for each context, e.g.:
|
||||
.Bd -literal
|
||||
export NNN_CONTEXT_COLORS='1234'
|
||||
------------------------------------ + -------------------------------------------------
|
||||
Key:Command | Description
|
||||
------------------------------------ + -------------------------------------------------
|
||||
c:!convert "$nnn" png:- | xclip | Copy image to clipboard
|
||||
-sel clipboard -t image/png* |
|
||||
C:!cp -rv "$nnn" "$nnn".cp* | Create a copy of the hovered file
|
||||
e:-!sudo -E vim "$nnn"* | Edit file as root in vim
|
||||
g:-!git diff | Show git diff
|
||||
h:-!hx "$nnn"* | Open hovered file in hx hex editor
|
||||
k:-!fuser -kiv "$nnn"* | Interactively kill process(es) using hovered file
|
||||
l:-!git log | Show git log
|
||||
n:-!vi /home/user/Dropbox/dir/note* | Take quick notes in a synced file/dir of notes
|
||||
p:-!less -iR "$nnn"* | Page through hovered file in less
|
||||
s:-!&smplayer -minigui "$nnn" | Play hovered media file, even unfinished download
|
||||
x:!chmod +x "$nnn" | Make the hovered file executable
|
||||
y:-!sync* | Flush cached writes
|
||||
------------------------------------ + -------------------------------------------------
|
||||
|
||||
codes: 0-black, 1-red, 2-green, 3-yellow, 4-blue (default), 5-magenta, 6-cyan, 7-white
|
||||
Online docs: https://github.com/jarun/nnn/tree/master/plugins
|
||||
.Ed
|
||||
.Pp
|
||||
\fBNNN_SSHFS_OPTS:\fR pass additional options to sshfs command:
|
||||
\fBNNN_ORDER:\fR directory-specific sort key.
|
||||
.Bd -literal
|
||||
export NNN_SSHFS_OPTS='sshfs -o reconnect,idmap=user,cache_timeout=3600'
|
||||
export NNN_ORDER='t:/home/user/Downloads;S:/tmp'
|
||||
|
||||
NOTE: The options must be preceded by `sshfs` and comma-separated without any space between them.
|
||||
.Ed
|
||||
.Pp
|
||||
\fBNNN_RCLONE_OPTS:\fR pass additional options to rclone command:
|
||||
.Bd -literal
|
||||
export NNN_RCLONE_OPTS='rclone mount --read-only --no-checksum'
|
||||
NOTE: Sort keys can be a/d/e/r/s/t/v (see program option -T).
|
||||
Capitalize to reverse (except 'r').
|
||||
Path must be absolute.
|
||||
|
||||
NOTE: The options must be preceded by `rclone` and max 5 flags are supported.
|
||||
Timestamps for entries modified/created within 5 minutes are shown in reverse.
|
||||
.Ed
|
||||
.Pp
|
||||
\fBNNN_IDLE_TIMEOUT:\fR set idle timeout (in seconds) to invoke terminal locker
|
||||
(default: disabled).
|
||||
.Pp
|
||||
\fBNNN_TRASH:\fR trash (instead of \fIdelete\fR) files to desktop Trash.
|
||||
\fBNNN_COLORS:\fR string of color numbers for each context, e.g.:
|
||||
.Bd -literal
|
||||
export NNN_TRASH=1
|
||||
# 8 color numbers:
|
||||
# 0-black, 1-red, 2-green, 3-yellow, 4-blue (default), 5-magenta, 6-cyan, 7-white
|
||||
export NNN_COLORS='1234'
|
||||
|
||||
# xterm 256 color numbers (converted to hex, 2 symbols per context):
|
||||
# see https://user-images.githubusercontent.com/1482942/93023823-46a6ba80-f5e1-11ea-9ea3-6a3c757704f4.png
|
||||
export NNN_COLORS='#0a1b2c3d'
|
||||
|
||||
# both (256 followed by 8 as fallback, separated by ';')
|
||||
export NNN_COLORS='#0a1b2c3d;1234'
|
||||
|
||||
NOTE: If only 256 colors are specified and the terminal doesn't support, default is used.
|
||||
.Ed
|
||||
.Pp
|
||||
\fBnnn:\fR this is a special variable set to the hovered entry before executing
|
||||
a command from the command prompt or spawning a shell.
|
||||
.Sh KNOWN ISSUES
|
||||
.Nm
|
||||
may not handle keypresses correctly when used with tmux (see issue #104 for
|
||||
more details). Set \fBTERM=xterm-256color\fR to address it.
|
||||
\fBNNN_FCOLORS:\fR specify file-type specific colors:
|
||||
.Bd -literal
|
||||
export NNN_FCOLORS='c1e2272e006033f7c6d6abc4'
|
||||
|
||||
Specify file-specific colors in xterm 256 color hex numbers (2 symbols per color).
|
||||
Order is strict, use 00 to omit/use default terminal color. Defaults:
|
||||
|
||||
------------------------- + --- + -------------
|
||||
Order | Hex | Color
|
||||
------------------------- + --- + -------------
|
||||
Block device | c1 | DarkSeaGreen1
|
||||
Char device | e2 | Yellow1
|
||||
Directory | 27 | DeepSkyBlue1
|
||||
Executable | 2e | Green1
|
||||
Regular | 00 | Normal
|
||||
Hard link | 60 | Plum4
|
||||
Symbolic link | 33 | Cyan1
|
||||
Missing OR file details | f7 | Grey62
|
||||
Orphaned symbolic link | c6 | DeepPink1
|
||||
FIFO | d6 | Orange1
|
||||
Socket | ab | MediumOrchid1
|
||||
Unknown OR 0B regular/exe | c4 | Red1
|
||||
------------------------- + --- + -------------
|
||||
|
||||
If the terminal supports xterm 256 colors or more, file-specific colors will be rendered.
|
||||
To force the 8-color scheme use option -C.
|
||||
If xterm 256 colors aren't supported, 8-color scheme will be used.
|
||||
.Ed
|
||||
.Pp
|
||||
\fBNNN_ARCHIVE:\fR archive extensions to be handled silently (default: bzip2, (g)zip, tar).
|
||||
.Bd -literal
|
||||
export NNN_ARCHIVE="\\\\.(7z|bz2|gz|tar|tgz|zip)$"
|
||||
|
||||
NOTE: Non-default formats may require a third-party utility.
|
||||
.Ed
|
||||
.Pp
|
||||
\fBNNN_ARCHMNT:\fR optional archive mounter utility (default: archivemount).
|
||||
.Bd -literal
|
||||
export NNN_ARCHIVE='fuse-archive'
|
||||
.Ed
|
||||
.Pp
|
||||
\fBNNN_SSHFS:\fR specify custom sshfs command with options:
|
||||
.Bd -literal
|
||||
export NNN_SSHFS='sshfs -o reconnect,idmap=user,cache_timeout=3600'
|
||||
|
||||
NOTE: The options must be comma-separated without any space between them.
|
||||
.Ed
|
||||
.Pp
|
||||
\fBNNN_RCLONE:\fR pass additional options to rclone command:
|
||||
.Bd -literal
|
||||
export NNN_RCLONE='rclone mount --read-only --no-checksum'
|
||||
|
||||
NOTE: The options must be preceded by "rclone" and max 5 flags are supported.
|
||||
.Ed
|
||||
.Pp
|
||||
\fBNNN_TRASH:\fR trash (instead of \fIrm -rf\fR) files to desktop Trash.
|
||||
.Bd -literal
|
||||
export NNN_TRASH=n
|
||||
# n=1: trash-cli, n=2: gio trash
|
||||
.Ed
|
||||
.Pp
|
||||
\fBNNN_SEL:\fR absolute path to custom selection file.
|
||||
.Bd -literal
|
||||
export NNN_SEL='/tmp/.sel'
|
||||
.Ed
|
||||
.Pp
|
||||
\fBNNN_FIFO:\fR path of a named pipe to write the hovered file path:
|
||||
.Bd -literal
|
||||
export NNN_FIFO='/tmp/nnn.fifo'
|
||||
|
||||
NOTES:
|
||||
1. Overridden by a temporary path with -a option.
|
||||
2. If the FIFO file doesn't exist it will be created,
|
||||
but not removed (unless it is generated by -a option).
|
||||
|
||||
Online docs: https://github.com/jarun/nnn/wiki/Live-previews
|
||||
.Ed
|
||||
.Pp
|
||||
\fBNNN_LOCKER:\fR terminal locker program.
|
||||
.Bd -literal
|
||||
export NNN_LOCKER='bmon -p wlp1s0'
|
||||
export NNN_LOCKER='cmatrix'
|
||||
.Ed
|
||||
.Pp
|
||||
\fBNNN_TMPFILE:\fR \fIalways\fR cd on quit and write the command in the file specified.
|
||||
.Bd -literal
|
||||
export NNN_TMPFILE='/tmp/.lastd'
|
||||
.Ed
|
||||
.Pp
|
||||
\fBNNN_HELP:\fR run a program and show the output on top of the program help page.
|
||||
.Bd -literal
|
||||
export NNN_HELP='fortune'
|
||||
.Ed
|
||||
.Pp
|
||||
\fBNNN_MCLICK:\fR key emulated by a middle mouse click.
|
||||
.Bd -literal
|
||||
export NNN_MCLICK='^R'
|
||||
|
||||
NOTE: Only the first character is considered if not a \fICtrl+key\fR combo.
|
||||
.Ed
|
||||
.Pp
|
||||
\fBnnn:\fR this is a special variable.
|
||||
.Bd -literal
|
||||
Set to the hovered file name before starting the command prompt or spawning a shell.
|
||||
.Ed
|
||||
.Pp
|
||||
\fBNO_COLOR:\fR disable ANSI color output (overridden by \fBNNN_COLORS\fR).
|
||||
.Sh AUTHORS
|
||||
.An Arun Prakash Jana Aq Mt engineerarun@gmail.com ,
|
||||
.An Lazaros Koromilas Aq Mt lostd@2f30.org ,
|
||||
|
|
|
@ -0,0 +1,30 @@
|
|||
<h1 align="center">User Patch Framework</h1>
|
||||
|
||||
This directory contains sizable user submitted patches that were rejected from mainline as they tend to be more subjective in nature.
|
||||
|
||||
The patches will be adapted on each release when necessary (v4.1 onwards). Each patch can be applied through its respective make variable during compilation. In case inter-patch merge conflicts occur, a compatibility patch is provided and will automatically be applied.
|
||||
|
||||
## List of patches
|
||||
|
||||
| Patch (a-z) | Description | Make var |
|
||||
| --- | --- | --- |
|
||||
| colemak | Key bindings for Colemak keyboard layout | `O_COLEMAK` |
|
||||
| gitstatus | Add git status column to the detail view. Provides command line flag `-G` to show column in normal mode. | `O_GITSTATUS` |
|
||||
| namefirst | Print filenames first in the detail view. Print user/group columns when a directory contains different users/groups. | `O_NAMEFIRST` |
|
||||
| restorepreview | Add pipe to close and restore [`preview-tui`](https://github.com/jarun/nnn/blob/master/plugins/preview-tui) for internal undetached edits (<kbd>e</kbd> key)| `O_RESTOREPREVIEW` |
|
||||
|
||||
To apply a patch, use the corresponding make variable, e.g.:
|
||||
|
||||
make O_NAMEFIRST=1
|
||||
|
||||
When contributing/adding a new patch, make sure to add the make variable to the patches array in `./misc/test/check-patches.sh` as well so that patch failures can be easily tested.
|
||||
|
||||
## Resolving patch conflicts
|
||||
|
||||
Patch conflicts can be checked locally by running `make checkpatches` or by running `./patches/check-patches.sh` manually.
|
||||
|
||||
Whenever patch conflicts occur on the latest master, pull requests resolving them are welcome. Let's say a conflict occurs in the `restorepreview` patch. The best way to resolve this conflict would be something along the lines of:
|
||||
|
||||
- Ensure you're on latest master and run `PATCH_OPTS="--merge" make O_RESTOREPREVIEW=1`. This will generate the conflict markers in `src/nnn.c`.
|
||||
- Next edit `src/nnn.c`, resolve the conflicts around the conflict markers(`<<<<<<<`), and save.
|
||||
- Then run `git diff > patch.diff && sed -i -e "/^$/{r patch.diff" -e "q;}" patches/restorepreview/mainline.diff` to update the patch.
|
|
@ -0,0 +1,29 @@
|
|||
#!/bin/bash
|
||||
#
|
||||
# Usage: ./misc/test/check-patches.sh
|
||||
#
|
||||
# Bash script that checks for any of the patches failing to apply.
|
||||
# Read patches/README.md for more information.
|
||||
|
||||
export PATCH_OPTS="--merge"
|
||||
patches=("O_COLEMAK" "O_GITSTATUS" "O_NAMEFIRST" "O_RESTOREPREVIEW")
|
||||
z=$(( 1 << ${#patches[@]} ))
|
||||
pid=$$
|
||||
ret=0
|
||||
trap 'ret=1' SIGUSR1
|
||||
|
||||
for ((n=1; n < z; ++n)); do
|
||||
for ((i=0; i < ${#patches[@]}; ++i)); do
|
||||
printf "%s=%d " "${patches[$i]}" "$(( (n & (1 << i)) != 0 ))"
|
||||
done | tee "/dev/stderr" | (
|
||||
make clean -s
|
||||
if ! xargs make 2>&1; then
|
||||
echo "[FAILED]" >&2
|
||||
kill -SIGUSR1 "$pid"
|
||||
else
|
||||
echo "[SUCCESS]" >&2
|
||||
fi
|
||||
git restore src
|
||||
) >/dev/null
|
||||
done
|
||||
exit "$ret"
|
|
@ -0,0 +1,134 @@
|
|||
diff --git a/src/nnn.c b/src/nnn.c
|
||||
index d7c53166..bb7ff3e8 100644
|
||||
--- a/src/nnn.c
|
||||
+++ b/src/nnn.c
|
||||
@@ -5149,12 +5149,12 @@ static void show_help(const char *path)
|
||||
"2(___n))\n"
|
||||
"0\n"
|
||||
"1NAVIGATION\n"
|
||||
- "9Up k Up%16PgUp ^U Page up\n"
|
||||
- "9Dn j Down%14PgDn ^D Page down\n"
|
||||
+ "9Up e Up%16PgUp ^U Page up\n"
|
||||
+ "9Dn n Down%14PgDn ^D Page down\n"
|
||||
"9Lt h Parent%12~ ` @ - ~, /, start, prev\n"
|
||||
- "5Ret Rt l Open%20' First file/match\n"
|
||||
- "9g ^A Top%21J Jump to entry/offset\n"
|
||||
- "9G ^E End%20^J Toggle auto-advance on open\n"
|
||||
+ "5Ret Rt i Open%20' First file/match\n"
|
||||
+ "9g ^E Top%21J Jump to entry/offset\n"
|
||||
+ "9G ^N End%20^J Toggle auto-advance on open\n"
|
||||
"8B (,) Book(mark)%11b ^/ Select bookmark\n"
|
||||
"a1-4 Context%11(Sh)Tab Cycle/new context\n"
|
||||
"62Esc ^Q Quit%19^y Next young\n"
|
||||
@@ -5162,27 +5162,27 @@ static void show_help(const char *path)
|
||||
"cq Quit context\n"
|
||||
"0\n"
|
||||
"1FILTER & PROMPT\n"
|
||||
- "c/ Filter%17^N Toggle type-to-nav\n"
|
||||
+ "c/ Filter%17^K Toggle type-to-nav\n"
|
||||
"aEsc Exit prompt%12^L Toggle last filter\n"
|
||||
"c. Toggle hidden%05Alt+Esc Unfilter, quit context\n"
|
||||
"0\n"
|
||||
"1FILES\n"
|
||||
- "9o ^O Open with%15n Create new/link\n"
|
||||
+ "9o ^O Open with%15c Create new/link\n"
|
||||
"9f ^F File stats%14d Detail mode toggle\n"
|
||||
"b^R Rename/dup%14r Batch rename\n"
|
||||
- "cz Archive%17e Edit file\n"
|
||||
+ "cz Archive%17y Edit file\n"
|
||||
"c* Toggle exe%14> Export list\n"
|
||||
"6Space + (Un)select%12m-m Select range/clear\n"
|
||||
"ca Select all%14A Invert sel\n"
|
||||
"9p ^P Copy here%12w ^W Cp/mv sel as\n"
|
||||
- "9v ^V Move here%15E Edit sel list\n"
|
||||
+ "9v ^V Move here%15l Edit sel list\n"
|
||||
"9x ^X Delete or trash%09S Listed sel size\n"
|
||||
"cX Delete (rm -rf)%07Esc Send to FIFO\n"
|
||||
"0\n"
|
||||
"1MISC\n"
|
||||
"8Alt ; Select plugin%11= Launch app\n"
|
||||
"9! ^] Shell%19] Cmd prompt\n"
|
||||
- "cc Connect remote%10u Unmount remote/archive\n"
|
||||
+ "cC Connect remote%10u Unmount remote/archive\n"
|
||||
"9t ^T Sort toggles%12s Manage session\n"
|
||||
"cT Set time type%110 Lock\n"
|
||||
"b^L Redraw%18? Help, conf\n"
|
||||
diff --git a/src/nnn.h b/src/nnn.h
|
||||
index bd500244..43b7fa22 100644
|
||||
--- a/src/nnn.h
|
||||
+++ b/src/nnn.h
|
||||
@@ -139,12 +139,12 @@ static struct key bindings[] = {
|
||||
{ '\r', SEL_OPEN },
|
||||
/* Pure navigate inside */
|
||||
{ KEY_RIGHT, SEL_NAV_IN },
|
||||
- { 'l', SEL_NAV_IN },
|
||||
+ { 'i', SEL_NAV_IN },
|
||||
/* Next */
|
||||
- { 'j', SEL_NEXT },
|
||||
+ { 'n', SEL_NEXT },
|
||||
{ KEY_DOWN, SEL_NEXT },
|
||||
/* Previous */
|
||||
- { 'k', SEL_PREV },
|
||||
+ { 'e', SEL_PREV },
|
||||
{ KEY_UP, SEL_PREV },
|
||||
/* Page down */
|
||||
{ KEY_NPAGE, SEL_PGDN },
|
||||
@@ -157,11 +157,11 @@ static struct key bindings[] = {
|
||||
/* First entry */
|
||||
{ KEY_HOME, SEL_HOME },
|
||||
{ 'g', SEL_HOME },
|
||||
- { CONTROL('A'), SEL_HOME },
|
||||
+ { CONTROL('E'), SEL_HOME },
|
||||
/* Last entry */
|
||||
{ KEY_END, SEL_END },
|
||||
{ 'G', SEL_END },
|
||||
- { CONTROL('E'), SEL_END },
|
||||
+ { CONTROL('N'), SEL_END },
|
||||
/* Go to first file */
|
||||
{ '\'', SEL_FIRST },
|
||||
/* Jump to an entry number/offset */
|
||||
@@ -179,7 +179,7 @@ static struct key bindings[] = {
|
||||
{ 'b', SEL_BMOPEN },
|
||||
{ CONTROL('_'), SEL_BMOPEN },
|
||||
/* Connect to server over SSHFS */
|
||||
- { 'c', SEL_REMOTE },
|
||||
+ { 'C', SEL_REMOTE },
|
||||
/* Cycle contexts in forward direction */
|
||||
{ '\t', SEL_CYCLE },
|
||||
/* Cycle contexts in reverse direction */
|
||||
@@ -202,7 +202,7 @@ static struct key bindings[] = {
|
||||
/* Filter */
|
||||
{ '/', SEL_FLTR },
|
||||
/* Toggle filter mode */
|
||||
- { CONTROL('N'), SEL_MFLTR },
|
||||
+ { CONTROL('K'), SEL_MFLTR },
|
||||
/* Toggle hide .dot files */
|
||||
{ '.', SEL_HIDDEN },
|
||||
/* Detailed listing */
|
||||
@@ -229,7 +229,7 @@ static struct key bindings[] = {
|
||||
/* Invert selection in current dir */
|
||||
{ 'A', SEL_SELINV },
|
||||
/* List, edit selection */
|
||||
- { 'E', SEL_SELEDIT },
|
||||
+ { 'l', SEL_SELEDIT },
|
||||
/* Copy from selection buffer */
|
||||
{ 'p', SEL_CP },
|
||||
{ CONTROL('P'), SEL_CP },
|
||||
@@ -247,7 +247,7 @@ static struct key bindings[] = {
|
||||
{ 'o', SEL_OPENWITH },
|
||||
{ CONTROL('O'), SEL_OPENWITH },
|
||||
/* Create a new file */
|
||||
- { 'n', SEL_NEW },
|
||||
+ { 'c', SEL_NEW },
|
||||
/* Show rename prompt */
|
||||
{ CONTROL('R'), SEL_RENAME },
|
||||
/* Rename contents of current dir */
|
||||
@@ -259,7 +259,7 @@ static struct key bindings[] = {
|
||||
/* Toggle auto-advance on file open */
|
||||
{ CONTROL('J'), SEL_AUTONEXT },
|
||||
/* Edit in EDITOR */
|
||||
- { 'e', SEL_EDIT },
|
||||
+ { 'y', SEL_EDIT },
|
||||
/* Run a plugin */
|
||||
{ ';', SEL_PLUGIN },
|
||||
/* Show total size of listed selection */
|
|
@ -0,0 +1,223 @@
|
|||
# Description: Add git status column to detail mode. Provides additional
|
||||
# command line flag -G which will render the git status
|
||||
# column also in normal mode. Vim plugin users may consider
|
||||
# adding the -G flag to their command override.
|
||||
#
|
||||
# Authors: Luuk van Baal
|
||||
|
||||
diff --git a/src/nnn.c b/src/nnn.c
|
||||
index 83ecdb90..4397944a 100644
|
||||
--- a/src/nnn.c
|
||||
+++ b/src/nnn.c
|
||||
@@ -270,6 +270,25 @@
|
||||
#define VFS_USED 1
|
||||
#define VFS_SIZE 2
|
||||
|
||||
+/* Git icons */
|
||||
+#ifdef NERD
|
||||
+#define GIT_ADD ""
|
||||
+#define GIT_DEL ""
|
||||
+#define GIT_IGN ""
|
||||
+#define GIT_MOD ""
|
||||
+#define GIT_NEW ""
|
||||
+#define GIT_NON "-"
|
||||
+#define GIT_UPD ""
|
||||
+#else
|
||||
+#define GIT_ADD "A"
|
||||
+#define GIT_DEL "D"
|
||||
+#define GIT_IGN "!"
|
||||
+#define GIT_MOD "M"
|
||||
+#define GIT_NEW "?"
|
||||
+#define GIT_NON "-"
|
||||
+#define GIT_UPD "U"
|
||||
+#endif
|
||||
+
|
||||
/* TYPE DEFINITIONS */
|
||||
typedef unsigned int uint_t;
|
||||
typedef unsigned char uchar_t;
|
||||
@@ -294,6 +313,7 @@ typedef struct entry {
|
||||
uid_t uid; /* 4 bytes */
|
||||
gid_t gid; /* 4 bytes */
|
||||
#endif
|
||||
+ char git_status[2][5];
|
||||
} *pEntry;
|
||||
|
||||
/* Selection marker */
|
||||
@@ -349,6 +369,7 @@ typedef struct {
|
||||
uint_t cliopener : 1; /* All-CLI app opener */
|
||||
uint_t waitedit : 1; /* For ops that can't be detached, used EDITOR */
|
||||
uint_t rollover : 1; /* Roll over at edges */
|
||||
+ uint_t normalgit : 1; /* Show git status in normal mode */
|
||||
} settings;
|
||||
|
||||
/* Non-persistent program-internal states (alphabeical order) */
|
||||
@@ -400,7 +421,17 @@ typedef struct {
|
||||
} session_header_t;
|
||||
#endif
|
||||
|
||||
+typedef struct {
|
||||
+ char status[2];
|
||||
+ char path[PATH_MAX];
|
||||
+} git_status_t;
|
||||
+
|
||||
/* GLOBALS */
|
||||
+struct {
|
||||
+ bool show;
|
||||
+ size_t len;
|
||||
+ git_status_t *statuses;
|
||||
+} git_statuses;
|
||||
|
||||
/* Configuration, contexts */
|
||||
static settings cfg = {
|
||||
@@ -3796,6 +3827,47 @@ static int get_kv_key(kv *kvarr, char *val, uchar_t max, uchar_t id)
|
||||
return -1;
|
||||
}
|
||||
|
||||
+static size_t get_git_statuses(const char *path)
|
||||
+{
|
||||
+ static char gst[] = "git -c core.quotePath= status -s --no-renames --ignored=matching -unormal . 2>/dev/null";
|
||||
+ FILE *fp = popen(gst, "r");
|
||||
+ char status[PATH_MAX];
|
||||
+ size_t pathindex, i = -1;
|
||||
+ git_statuses.show = FALSE;
|
||||
+
|
||||
+ while (fgets(status, PATH_MAX, fp)) {
|
||||
+ pathindex = (status[3] == '"') ? 4 : 3;
|
||||
+ if (!cfg.showhidden && status[pathindex] == '.')
|
||||
+ continue;
|
||||
+ status[xstrlen(status) - pathindex + 2] = '\0';
|
||||
+ git_statuses.statuses = xrealloc(git_statuses.statuses, sizeof(git_status_t) * (++i + 1));
|
||||
+ git_statuses.statuses[i].status[0] = status[0];
|
||||
+ git_statuses.statuses[i].status[1] = status[1];
|
||||
+ mkpath(path, status + pathindex, git_statuses.statuses[i].path);
|
||||
+ }
|
||||
+
|
||||
+ pclose(fp);
|
||||
+ return (i + 1);
|
||||
+}
|
||||
+
|
||||
+static void set_git_status(char status[][5], uint_t nr)
|
||||
+{
|
||||
+ for (int j = 0; j < 2; j++) {
|
||||
+ if (status[j][0] == '-')
|
||||
+ switch (git_statuses.statuses[nr].status[j]) {
|
||||
+ case ' ': xstrsncpy(status[j], GIT_NON, 4); break;
|
||||
+ case 'M': xstrsncpy(status[j], GIT_MOD, 4); break;
|
||||
+ case 'A': xstrsncpy(status[j], GIT_ADD, 4); break;
|
||||
+ case '?': xstrsncpy(status[j], GIT_NEW, 4); break;
|
||||
+ case '!': xstrsncpy(status[j], GIT_IGN, 4); break;
|
||||
+ case 'D': xstrsncpy(status[j], GIT_DEL, 4); break;
|
||||
+ case 'U': xstrsncpy(status[j], GIT_UPD, 4); break;
|
||||
+ }
|
||||
+ }
|
||||
+ if (git_statuses.statuses[nr].status[1] != '!')
|
||||
+ git_statuses.show = TRUE;
|
||||
+}
|
||||
+
|
||||
static void resetdircolor(int flags)
|
||||
{
|
||||
/* Directories are always shown on top, clear the color when moving to first file */
|
||||
@@ -4123,6 +4195,10 @@ static void printent(const struct entry *ent, uint_t namecols, bool sel)
|
||||
|
||||
uchar_t color_pair = get_color_pair_name_ind(ent, &ind, &attrs);
|
||||
|
||||
+ if (git_statuses.show && (cfg.showdetail || cfg.normalgit))
|
||||
+ printw("%*s%s%s", (cfg.normalgit && !cfg.showdetail) ? 1 : 0, "",
|
||||
+ ent->git_status[0], ent->git_status[1]);
|
||||
+
|
||||
addch((ent->flags & FILE_SELECTED) ? '+' | A_REVERSE | A_BOLD : ' ');
|
||||
|
||||
if (g_state.oldcolor)
|
||||
@@ -5592,6 +5668,11 @@ static int dentfill(char *path, struct entry **ppdents)
|
||||
attron(COLOR_PAIR(cfg.curctx + 1));
|
||||
}
|
||||
|
||||
+ char linkpath[PATH_MAX];
|
||||
+ if ((git_statuses.len = get_git_statuses(path)))
|
||||
+ if (!realpath(path, linkpath))
|
||||
+ printwarn(NULL);
|
||||
+
|
||||
#if _POSIX_C_SOURCE >= 200112L
|
||||
posix_fadvise(fd, 0, 0, POSIX_FADV_SEQUENTIAL);
|
||||
#endif
|
||||
@@ -5792,6 +5873,29 @@ static int dentfill(char *path, struct entry **ppdents)
|
||||
#endif
|
||||
}
|
||||
|
||||
+ if (git_statuses.len) {
|
||||
+ char dentpath[PATH_MAX];
|
||||
+ size_t pathlen = mkpath(linkpath, dentp->name, dentpath);
|
||||
+ dentp->git_status[0][0] = dentp->git_status[1][0] = '-';
|
||||
+ dentp->git_status[0][1] = dentp->git_status[1][1] = '\0';
|
||||
+
|
||||
+ if (dentp->flags & DIR_OR_DIRLNK) {
|
||||
+ char prefix[PATH_MAX];
|
||||
+ memccpy(prefix, dentpath, '\0', PATH_MAX);
|
||||
+ prefix[pathlen - 1] = '/';
|
||||
+
|
||||
+ for (size_t i = 0; i < git_statuses.len; ++i)
|
||||
+ if (is_prefix(git_statuses.statuses[i].path, prefix, pathlen))
|
||||
+ set_git_status(dentp->git_status, i);
|
||||
+ } else {
|
||||
+ for (size_t i = 0; i < git_statuses.len; ++i)
|
||||
+ if (!xstrcmp(git_statuses.statuses[i].path, dentpath)) {
|
||||
+ set_git_status(dentp->git_status, i);
|
||||
+ break;
|
||||
+ }
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
++ndents;
|
||||
} while ((dp = readdir(dirp)));
|
||||
|
||||
@@ -6361,11 +6465,12 @@ static int adjust_cols(int n)
|
||||
#endif
|
||||
if (cfg.showdetail) {
|
||||
/* Fallback to light mode if less than 35 columns */
|
||||
- if (n < 36)
|
||||
+ if (n < 38)
|
||||
cfg.showdetail ^= 1;
|
||||
else /* 2 more accounted for below */
|
||||
- n -= 32;
|
||||
- }
|
||||
+ n -= (git_statuses.show ? 34 : 32);
|
||||
+ } else if (cfg.normalgit && git_statuses.show)
|
||||
+ n -= 3;
|
||||
|
||||
/* 2 columns for preceding space and indicator */
|
||||
return (n - 2);
|
||||
@@ -8143,6 +8248,7 @@ static void usage(void)
|
||||
" -F val fifo mode [0:preview 1:explore]\n"
|
||||
#endif
|
||||
" -g regex filters\n"
|
||||
+ " -G always show git status\n"
|
||||
" -H show hidden files\n"
|
||||
" -i show current file info\n"
|
||||
" -J no auto-advance on selection\n"
|
||||
@@ -8282,6 +8388,7 @@ static void cleanup(void)
|
||||
fflush(stdout);
|
||||
}
|
||||
#endif
|
||||
+ free(git_statuses.statuses);
|
||||
free(selpath);
|
||||
free(plgpath);
|
||||
free(cfgpath);
|
||||
@@ -8326,7 +8433,7 @@ int main(int argc, char *argv[])
|
||||
|
||||
while ((opt = (env_opts_id > 0
|
||||
? env_opts[--env_opts_id]
|
||||
- : getopt(argc, argv, "aAb:BcCdDeEfF:gHiJKl:nNop:P:QrRs:St:T:uUVxh"))) != -1) {
|
||||
+ : getopt(argc, argv, "aAb:BcCdDeEfF:gGHiJKl:nNop:P:QrRs:St:T:uUVxh"))) != -1) {
|
||||
switch (opt) {
|
||||
#ifndef NOFIFO
|
||||
case 'a':
|
||||
@@ -8380,6 +8487,9 @@ int main(int argc, char *argv[])
|
||||
cfg.regex = 1;
|
||||
filterfn = &visible_re;
|
||||
break;
|
||||
+ case 'G':
|
||||
+ cfg.normalgit = 1;
|
||||
+ break;
|
||||
case 'H':
|
||||
cfg.showhidden = 1;
|
||||
break;
|
|
@ -0,0 +1,226 @@
|
|||
# Description: Add git status column to detail mode. Provides additional
|
||||
# command line flag -G which will render the git status
|
||||
# column also in normal mode. Vim plugin users may consider
|
||||
# adding the -G flag to their command override.
|
||||
# Compatibility patch for the namefirst patch.
|
||||
#
|
||||
# Authors: Luuk van Baal
|
||||
|
||||
diff --git a/src/nnn.c b/src/nnn.c
|
||||
index 88538787..d4af7c43 100644
|
||||
--- a/src/nnn.c
|
||||
+++ b/src/nnn.c
|
||||
@@ -270,6 +270,25 @@
|
||||
#define VFS_USED 1
|
||||
#define VFS_SIZE 2
|
||||
|
||||
+/* Git icons */
|
||||
+#ifdef NERD
|
||||
+#define GIT_ADD ""
|
||||
+#define GIT_DEL ""
|
||||
+#define GIT_IGN ""
|
||||
+#define GIT_MOD ""
|
||||
+#define GIT_NEW ""
|
||||
+#define GIT_NON "-"
|
||||
+#define GIT_UPD ""
|
||||
+#else
|
||||
+#define GIT_ADD "A"
|
||||
+#define GIT_DEL "D"
|
||||
+#define GIT_IGN "!"
|
||||
+#define GIT_MOD "M"
|
||||
+#define GIT_NEW "?"
|
||||
+#define GIT_NON "-"
|
||||
+#define GIT_UPD "U"
|
||||
+#endif
|
||||
+
|
||||
/* TYPE DEFINITIONS */
|
||||
typedef unsigned int uint_t;
|
||||
typedef unsigned char uchar_t;
|
||||
@@ -294,6 +313,7 @@ typedef struct entry {
|
||||
uid_t uid; /* 4 bytes */
|
||||
gid_t gid; /* 4 bytes */
|
||||
#endif
|
||||
+ char git_status[2][5];
|
||||
} *pEntry;
|
||||
|
||||
/* Selection marker */
|
||||
@@ -349,6 +369,7 @@ typedef struct {
|
||||
uint_t cliopener : 1; /* All-CLI app opener */
|
||||
uint_t waitedit : 1; /* For ops that can't be detached, used EDITOR */
|
||||
uint_t rollover : 1; /* Roll over at edges */
|
||||
+ uint_t normalgit : 1; /* Show git status in normal mode */
|
||||
} settings;
|
||||
|
||||
/* Non-persistent program-internal states (alphabeical order) */
|
||||
@@ -404,7 +425,17 @@ static struct {
|
||||
ushort_t maxnameln, maxsizeln, maxuidln, maxgidln, maxentln, uidln, gidln, printguid;
|
||||
} dtls;
|
||||
|
||||
+typedef struct {
|
||||
+ char status[2];
|
||||
+ char path[PATH_MAX];
|
||||
+} git_status_t;
|
||||
+
|
||||
/* GLOBALS */
|
||||
+struct {
|
||||
+ bool show;
|
||||
+ size_t len;
|
||||
+ git_status_t *statuses;
|
||||
+} git_statuses;
|
||||
|
||||
/* Configuration, contexts */
|
||||
static settings cfg = {
|
||||
@@ -3804,6 +3835,47 @@ static int get_kv_key(kv *kvarr, char *val, uchar_t max, uchar_t id)
|
||||
return -1;
|
||||
}
|
||||
|
||||
+static size_t get_git_statuses(const char *path)
|
||||
+{
|
||||
+ static char gst[] = "git -c core.quotePath= status -s --no-renames --ignored=matching -unormal . 2>/dev/null";
|
||||
+ FILE *fp = popen(gst, "r");
|
||||
+ char status[PATH_MAX];
|
||||
+ size_t pathindex, i = -1;
|
||||
+ git_statuses.show = FALSE;
|
||||
+
|
||||
+ while (fgets(status, PATH_MAX, fp)) {
|
||||
+ pathindex = (status[3] == '"') ? 4 : 3;
|
||||
+ if (!cfg.showhidden && status[pathindex] == '.')
|
||||
+ continue;
|
||||
+ status[xstrlen(status) - pathindex + 2] = '\0';
|
||||
+ git_statuses.statuses = xrealloc(git_statuses.statuses, sizeof(git_status_t) * (++i + 1));
|
||||
+ git_statuses.statuses[i].status[0] = status[0];
|
||||
+ git_statuses.statuses[i].status[1] = status[1];
|
||||
+ mkpath(path, status + pathindex, git_statuses.statuses[i].path);
|
||||
+ }
|
||||
+
|
||||
+ pclose(fp);
|
||||
+ return (i + 1);
|
||||
+}
|
||||
+
|
||||
+static void set_git_status(char status[][5], uint_t nr)
|
||||
+{
|
||||
+ for (int j = 0; j < 2; j++) {
|
||||
+ if (status[j][0] == '-')
|
||||
+ switch (git_statuses.statuses[nr].status[j]) {
|
||||
+ case ' ': xstrsncpy(status[j], GIT_NON, 4); break;
|
||||
+ case 'M': xstrsncpy(status[j], GIT_MOD, 4); break;
|
||||
+ case 'A': xstrsncpy(status[j], GIT_ADD, 4); break;
|
||||
+ case '?': xstrsncpy(status[j], GIT_NEW, 4); break;
|
||||
+ case '!': xstrsncpy(status[j], GIT_IGN, 4); break;
|
||||
+ case 'D': xstrsncpy(status[j], GIT_DEL, 4); break;
|
||||
+ case 'U': xstrsncpy(status[j], GIT_UPD, 4); break;
|
||||
+ }
|
||||
+ }
|
||||
+ if (git_statuses.statuses[nr].status[1] != '!')
|
||||
+ git_statuses.show = TRUE;
|
||||
+}
|
||||
+
|
||||
static void resetdircolor(int flags)
|
||||
{
|
||||
/* Directories are always shown on top, clear the color when moving to first file */
|
||||
@@ -4104,6 +4176,9 @@ static void printent(const struct entry *ent, uint_t namecols, bool sel)
|
||||
int attrs = 0, namelen;
|
||||
uchar_t color_pair = get_color_pair_name_ind(ent, &ind, &attrs);
|
||||
|
||||
+ if (git_statuses.show && (cfg.showdetail || cfg.normalgit))
|
||||
+ printw(" %s%s", ent->git_status[0], ent->git_status[1]);
|
||||
+
|
||||
addch((ent->flags & FILE_SELECTED) ? '+' | A_REVERSE | A_BOLD : ' ');
|
||||
|
||||
if (g_state.oldcolor)
|
||||
@@ -5598,6 +5673,11 @@ static int dentfill(char *path, struct entry **ppdents)
|
||||
attron(COLOR_PAIR(cfg.curctx + 1));
|
||||
}
|
||||
|
||||
+ char linkpath[PATH_MAX];
|
||||
+ if ((git_statuses.len = get_git_statuses(path)))
|
||||
+ if (!realpath(path, linkpath))
|
||||
+ printwarn(NULL);
|
||||
+
|
||||
#if _POSIX_C_SOURCE >= 200112L
|
||||
posix_fadvise(fd, 0, 0, POSIX_FADV_SEQUENTIAL);
|
||||
#endif
|
||||
@@ -5798,6 +5878,29 @@ static int dentfill(char *path, struct entry **ppdents)
|
||||
#endif
|
||||
}
|
||||
|
||||
+ if (git_statuses.len) {
|
||||
+ char dentpath[PATH_MAX];
|
||||
+ size_t pathlen = mkpath(linkpath, dentp->name, dentpath);
|
||||
+ dentp->git_status[0][0] = dentp->git_status[1][0] = '-';
|
||||
+ dentp->git_status[0][1] = dentp->git_status[1][1] = '\0';
|
||||
+
|
||||
+ if (dentp->flags & DIR_OR_DIRLNK) {
|
||||
+ char prefix[PATH_MAX];
|
||||
+ memccpy(prefix, dentpath, '\0', PATH_MAX);
|
||||
+ prefix[pathlen - 1] = '/';
|
||||
+
|
||||
+ for (size_t i = 0; i < git_statuses.len; ++i)
|
||||
+ if (is_prefix(git_statuses.statuses[i].path, prefix, pathlen))
|
||||
+ set_git_status(dentp->git_status, i);
|
||||
+ } else {
|
||||
+ for (size_t i = 0; i < git_statuses.len; ++i)
|
||||
+ if (!xstrcmp(git_statuses.statuses[i].path, dentpath)) {
|
||||
+ set_git_status(dentp->git_status, i);
|
||||
+ break;
|
||||
+ }
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
++ndents;
|
||||
} while ((dp = readdir(dirp)));
|
||||
|
||||
@@ -6362,7 +6465,8 @@ static int adjust_cols(int n)
|
||||
cfg.showdetail ^= 1;
|
||||
else /* 2 more accounted for below */
|
||||
n -= (dtls.maxentln - 2 - dtls.maxnameln);
|
||||
- }
|
||||
+ } else if (cfg.normalgit && git_statuses.show)
|
||||
+ n -= 3;
|
||||
|
||||
/* 2 columns for preceding space and indicator */
|
||||
return (n - 2);
|
||||
@@ -6517,7 +6621,7 @@ static void redraw(char *path)
|
||||
}
|
||||
#endif
|
||||
}
|
||||
- dtls.maxentln = dtls.maxnameln + dtls.maxsizeln + (dtls.printguid ? (dtls.maxuidln + dtls.maxgidln + 29) : 26);
|
||||
+ dtls.maxentln = dtls.maxnameln + dtls.maxsizeln + (dtls.printguid ? (dtls.maxuidln + dtls.maxgidln + 3) : 0) + (git_statuses.show ? 29 : 26);
|
||||
}
|
||||
|
||||
ncols = adjust_cols(ncols);
|
||||
@@ -8153,6 +8257,7 @@ static void usage(void)
|
||||
" -F val fifo mode [0:preview 1:explore]\n"
|
||||
#endif
|
||||
" -g regex filters\n"
|
||||
+ " -G always show git status\n"
|
||||
" -H show hidden files\n"
|
||||
" -i show current file info\n"
|
||||
" -J no auto-advance on selection\n"
|
||||
@@ -8292,6 +8397,7 @@ static void cleanup(void)
|
||||
fflush(stdout);
|
||||
}
|
||||
#endif
|
||||
+ free(git_statuses.statuses);
|
||||
free(selpath);
|
||||
free(plgpath);
|
||||
free(cfgpath);
|
||||
@@ -8336,7 +8442,7 @@ int main(int argc, char *argv[])
|
||||
|
||||
while ((opt = (env_opts_id > 0
|
||||
? env_opts[--env_opts_id]
|
||||
- : getopt(argc, argv, "aAb:BcCdDeEfF:gHiJKl:nNop:P:QrRs:St:T:uUVxh"))) != -1) {
|
||||
+ : getopt(argc, argv, "aAb:BcCdDeEfF:gGHiJKl:nNop:P:QrRs:St:T:uUVxh"))) != -1) {
|
||||
switch (opt) {
|
||||
#ifndef NOFIFO
|
||||
case 'a':
|
||||
@@ -8390,6 +8496,9 @@ int main(int argc, char *argv[])
|
||||
cfg.regex = 1;
|
||||
filterfn = &visible_re;
|
||||
break;
|
||||
+ case 'G':
|
||||
+ cfg.normalgit = 1;
|
||||
+ break;
|
||||
case 'H':
|
||||
cfg.showhidden = 1;
|
||||
break;
|
|
@ -0,0 +1,227 @@
|
|||
# Description: Prints filenames first in the detail view. Prints user/group
|
||||
# columns when a directory contains different users/groups.
|
||||
#
|
||||
# Author: Luuk van Baal
|
||||
|
||||
diff --git a/src/nnn.c b/src/nnn.c
|
||||
index f8a2c58..9802a1f 100644
|
||||
--- a/src/nnn.c
|
||||
+++ b/src/nnn.c
|
||||
@@ -394,6 +394,10 @@ typedef struct {
|
||||
} session_header_t;
|
||||
#endif
|
||||
|
||||
+static struct {
|
||||
+ ushort_t maxnameln, maxsizeln, maxuidln, maxgidln, maxentln, uidln, gidln, printguid;
|
||||
+} dtls;
|
||||
+
|
||||
/* GLOBALS */
|
||||
|
||||
/* Configuration, contexts */
|
||||
@@ -1070,10 +1074,12 @@ static char *getpwname(uid_t uid)
|
||||
static char *namecache;
|
||||
|
||||
if (uidcache != uid) {
|
||||
+ if (dtls.maxuidln && !dtls.printguid) dtls.printguid = 1;
|
||||
struct passwd *pw = getpwuid(uid);
|
||||
|
||||
uidcache = uid;
|
||||
namecache = pw ? pw->pw_name : NULL;
|
||||
+ dtls.uidln = xstrlen(namecache ? namecache : xitoa(uid));
|
||||
}
|
||||
|
||||
return namecache ? namecache : xitoa(uid);
|
||||
@@ -1085,10 +1091,12 @@ static char *getgrname(gid_t gid)
|
||||
static char *grpcache;
|
||||
|
||||
if (gidcache != gid) {
|
||||
+ if (dtls.maxgidln && !dtls.printguid) dtls.printguid = 1;
|
||||
struct group *gr = getgrgid(gid);
|
||||
|
||||
gidcache = gid;
|
||||
grpcache = gr ? gr->gr_name : NULL;
|
||||
+ dtls.gidln = xstrlen(grpcache ? grpcache : xitoa(gid));
|
||||
}
|
||||
|
||||
return grpcache ? grpcache : xitoa(gid);
|
||||
@@ -3834,14 +3842,13 @@ static void resetdircolor(int flags)
|
||||
* Max supported str length: NAME_MAX;
|
||||
*/
|
||||
#ifdef NOLC
|
||||
-static char *unescape(const char *str, uint_t maxcols)
|
||||
+static size_t unescape(const char *str, uint_t maxcols)
|
||||
{
|
||||
char * const wbuf = g_buf;
|
||||
char *buf = wbuf;
|
||||
-
|
||||
- xstrsncpy(wbuf, str, maxcols);
|
||||
+ size_t len = xstrsncpy(wbuf, str, maxcols);
|
||||
#else
|
||||
-static wchar_t *unescape(const char *str, uint_t maxcols)
|
||||
+static size_t unescape(const char *str, uint_t maxcols)
|
||||
{
|
||||
wchar_t * const wbuf = (wchar_t *)g_buf;
|
||||
wchar_t *buf = wbuf;
|
||||
@@ -3866,7 +3873,7 @@ static wchar_t *unescape(const char *str, uint_t maxcols)
|
||||
++buf;
|
||||
}
|
||||
|
||||
- return wbuf;
|
||||
+ return len;
|
||||
}
|
||||
|
||||
static off_t get_size(off_t size, off_t *pval, int comp)
|
||||
@@ -4228,38 +4235,13 @@ static void printent(int pdents_index, uint_t namecols, bool sel)
|
||||
{
|
||||
const struct entry *ent = &pdents[pdents_index];
|
||||
char ind = '\0';
|
||||
- int attrs;
|
||||
-
|
||||
- if (cfg.showdetail) {
|
||||
- int type = ent->mode & S_IFMT;
|
||||
- char perms[6] = {' ', ' ', (char)('0' + ((ent->mode >> 6) & 7)),
|
||||
- (char)('0' + ((ent->mode >> 3) & 7)),
|
||||
- (char)('0' + (ent->mode & 7)), '\0'};
|
||||
-
|
||||
- addch(' ');
|
||||
- attrs = g_state.oldcolor ? (resetdircolor(ent->flags), A_DIM)
|
||||
- : (fcolors[C_MIS] ? COLOR_PAIR(C_MIS) : 0);
|
||||
- if (attrs)
|
||||
- attron(attrs);
|
||||
-
|
||||
- /* Print details */
|
||||
- print_time(&ent->sec, ent->flags);
|
||||
-
|
||||
- printw("%s%9s ", perms, (type == S_IFREG || type == S_IFDIR)
|
||||
- ? coolsize(cfg.blkorder ? (blkcnt_t)ent->blocks << blk_shift : ent->size)
|
||||
- : (type = (uchar_t)get_detail_ind(ent->mode), (char *)&type));
|
||||
-
|
||||
- if (attrs)
|
||||
- attroff(attrs);
|
||||
- }
|
||||
+ int attrs = 0, namelen;
|
||||
|
||||
if (g_state.showlines) {
|
||||
ptrdiff_t rel_num = pdents_index - cur;
|
||||
printw(rel_num == 0 ? "%4td" : "%+4td", rel_num);
|
||||
}
|
||||
|
||||
- attrs = 0;
|
||||
-
|
||||
uchar_t color_pair = get_color_pair_name_ind(ent, &ind, &attrs);
|
||||
|
||||
addch((ent->flags & FILE_SELECTED) ? '+' | A_REVERSE | A_BOLD : ' ');
|
||||
@@ -4284,15 +4266,40 @@ static void printent(int pdents_index, uint_t namecols, bool sel)
|
||||
++namecols;
|
||||
|
||||
#ifndef NOLC
|
||||
- addwstr(unescape(ent->name, namecols));
|
||||
+ addwstr((namelen = unescape(ent->name, namecols), (wchar_t *)g_buf));
|
||||
#else
|
||||
- addstr(unescape(ent->name, MIN(namecols, ent->nlen) + 1));
|
||||
+ addstr((namelen = unescape(ent->name, MIN(namecols, ent->nlen) + 1), (char *)g_buf));
|
||||
#endif
|
||||
|
||||
- if (attrs)
|
||||
+ if (!sel && attrs)
|
||||
attroff(attrs);
|
||||
if (ind)
|
||||
addch(ind);
|
||||
+ if (cfg.showdetail) {
|
||||
+ int type = ent->mode & S_IFMT;
|
||||
+ char perms[6] = {(char)('0' + ((ent->mode >> 6) & 7)),
|
||||
+ (char)('0' + ((ent->mode >> 3) & 7)),
|
||||
+ (char)('0' + (ent->mode & 7)), ' ', ' ', '\0'}, *size = NULL;
|
||||
+
|
||||
+ if (attrs)
|
||||
+ attron(attrs);
|
||||
+ if (!g_state.oldcolor && (type == S_IFDIR || (type == S_IFLNK && ent->flags & DIR_OR_DIRLNK)))
|
||||
+ attroff(A_BOLD);
|
||||
+ int sizelen = (type == S_IFREG || type == S_IFDIR) ? xstrlen(size = coolsize(cfg.blkorder ? ent->blocks << blk_shift : ent->size)) : 1;
|
||||
+ printw("%*c%*s%s%s", 1 + MIN(namecols, dtls.maxnameln + (uint_t)(ind ? 0 : 1)) - namelen, ' ',
|
||||
+ dtls.maxsizeln - sizelen, "", size ? size : (type = (uchar_t)get_detail_ind(ent->mode), (char *)&type), " ");
|
||||
+#ifndef NOUG
|
||||
+ if (g_state.uidgid && dtls.printguid) {
|
||||
+ addstr(getpwname(ent->uid));
|
||||
+ printw("%*c%s", dtls.maxuidln + 1 - dtls.uidln, ' ', getgrname(ent->gid));
|
||||
+ printw("%*c", dtls.maxgidln + 2 - dtls.gidln, ' ');
|
||||
+ }
|
||||
+#endif
|
||||
+ addstr(perms);
|
||||
+ print_time(&ent->sec, ent->flags);
|
||||
+ }
|
||||
+ if (attrs)
|
||||
+ attroff(attrs);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -6527,26 +6534,19 @@ static void statusbar(char *path)
|
||||
tocursor();
|
||||
}
|
||||
|
||||
-static inline void markhovered(void)
|
||||
-{
|
||||
- if (cfg.showdetail && ndents) { /* Bold forward arrowhead */
|
||||
- tocursor();
|
||||
- addch('>' | A_BOLD);
|
||||
- }
|
||||
-}
|
||||
-
|
||||
static int adjust_cols(int n)
|
||||
{
|
||||
/* Calculate the number of cols available to print entry name */
|
||||
#ifdef ICONS_ENABLED
|
||||
n -= (g_state.oldcolor ? 0 : ICON_SIZE + ICON_PADDING_LEFT_LEN + ICON_PADDING_RIGHT_LEN);
|
||||
#endif
|
||||
+
|
||||
if (cfg.showdetail) {
|
||||
/* Fallback to light mode if less than 35 columns */
|
||||
- if (n < 36)
|
||||
+ if (n < (dtls.maxentln + 1 - dtls.maxnameln))
|
||||
cfg.showdetail ^= 1;
|
||||
else /* 2 more accounted for below */
|
||||
- n -= 32;
|
||||
+ n -= (dtls.maxentln - 2 - dtls.maxnameln);
|
||||
}
|
||||
|
||||
/* 2 columns for preceding space and indicator */
|
||||
@@ -6412,8 +6411,6 @@ static void draw_line(int ncols)
|
||||
/* Must reset e.g. no files in dir */
|
||||
if (dir)
|
||||
attroff(COLOR_PAIR(cfg.curctx + 1) | A_BOLD);
|
||||
-
|
||||
- markhovered();
|
||||
}
|
||||
|
||||
static void redraw(char *path)
|
||||
@@ -6521,6 +6518,21 @@ static void redraw(char *path)
|
||||
|
||||
onscreen = MIN(onscreen + curscroll, ndents);
|
||||
|
||||
+ if (cfg.showdetail) {
|
||||
+ ushort_t lenbuf = dtls.maxnameln = dtls.maxsizeln = dtls.maxuidln = dtls.maxgidln = dtls.printguid = 0;
|
||||
+ for (i = curscroll; i < onscreen; ++i) {
|
||||
+ if ((lenbuf = pdents[i].nlen - 1) > dtls.maxnameln) dtls.maxnameln = lenbuf;
|
||||
+ if ((lenbuf = xstrlen(coolsize(cfg.blkorder ? pdents[i].blocks << blk_shift : pdents[i].size))) > dtls.maxsizeln) dtls.maxsizeln = lenbuf;
|
||||
+#ifndef NOUG
|
||||
+ if (g_state.uidgid) {
|
||||
+ if ((getpwname(pdents[i].uid), dtls.uidln) > dtls.maxuidln) dtls.maxuidln = dtls.uidln;
|
||||
+ if ((getgrname(pdents[i].gid), dtls.gidln) > dtls.maxgidln) dtls.maxgidln = dtls.gidln;
|
||||
+ }
|
||||
+#endif
|
||||
+ }
|
||||
+ dtls.maxentln = dtls.maxnameln + dtls.maxsizeln + (dtls.printguid ? (dtls.maxuidln + dtls.maxgidln + 29) : 26);
|
||||
+ }
|
||||
+
|
||||
ncols = adjust_cols(ncols);
|
||||
|
||||
int len = scanselforpath(path, FALSE);
|
||||
@@ -6551,7 +6563,7 @@ static void redraw(char *path)
|
||||
#endif
|
||||
}
|
||||
|
||||
- markhovered();
|
||||
+ statusbar(path);
|
||||
}
|
||||
|
||||
static bool cdprep(char *lastdir, char *lastname, char *path, char *newpath)
|
|
@ -0,0 +1,269 @@
|
|||
# Description: Adds preview pipe to enable closing and re-opening the preview
|
||||
# pane when running an undetached editor. If you are using vim
|
||||
# you might experience incorrectly resized window. Consider adding
|
||||
# the following to your vimrc:
|
||||
# autocmd VimEnter * :silent exec "!kill -s WINCH $PPID"
|
||||
#
|
||||
# Authors: Luuk van Baal
|
||||
|
||||
diff --git a/src/nnn.c b/src/nnn.c
|
||||
index 0388b23c..66d3316a 100644
|
||||
--- a/src/nnn.c
|
||||
+++ b/src/nnn.c
|
||||
@@ -391,7 +391,8 @@ typedef struct {
|
||||
uint_t usebsdtar : 1; /* Use bsdtar as default archive utility */
|
||||
uint_t xprompt : 1; /* Use native prompt instead of readline prompt */
|
||||
uint_t showlines : 1; /* Show line numbers */
|
||||
- uint_t reserved : 3; /* Adjust when adding/removing a field */
|
||||
+ uint_t previewer : 1; /* Run state of previewer */
|
||||
+ uint_t reserved : 2; /* Adjust when adding/removing a field */
|
||||
} runstate;
|
||||
|
||||
/* Contexts or workspaces */
|
||||
@@ -516,6 +517,9 @@ alignas(max_align_t) static char g_tmpfpath[TMP_LEN_MAX];
|
||||
/* Buffer to store plugins control pipe location */
|
||||
alignas(max_align_t) static char g_pipepath[TMP_LEN_MAX];
|
||||
|
||||
+/* Buffer to store preview plugins control pipe location */
|
||||
+static char g_ppipepath[TMP_LEN_MAX] __attribute__ ((aligned));
|
||||
+
|
||||
/* Non-persistent runtime states */
|
||||
static runstate g_state;
|
||||
|
||||
@@ -696,12 +700,13 @@ static const char * const messages[] = {
|
||||
#define NNN_FCOLORS 5
|
||||
#define NNNLVL 6
|
||||
#define NNN_PIPE 7
|
||||
-#define NNN_MCLICK 8
|
||||
-#define NNN_SEL 9
|
||||
-#define NNN_ARCHIVE 10
|
||||
-#define NNN_ORDER 11
|
||||
-#define NNN_HELP 12 /* strings end here */
|
||||
-#define NNN_TRASH 13 /* flags begin here */
|
||||
+#define NNN_PPIPE 8
|
||||
+#define NNN_MCLICK 9
|
||||
+#define NNN_SEL 10
|
||||
+#define NNN_ARCHIVE 11
|
||||
+#define NNN_ORDER 12
|
||||
+#define NNN_HELP 13 /* strings end here */
|
||||
+#define NNN_TRASH 14 /* flags begin here */
|
||||
|
||||
static const char * const env_cfg[] = {
|
||||
"NNN_OPTS",
|
||||
@@ -712,6 +717,7 @@ static const char * const env_cfg[] = {
|
||||
"NNN_FCOLORS",
|
||||
"NNNLVL",
|
||||
"NNN_PIPE",
|
||||
+ "NNN_PPIPE",
|
||||
"NNN_MCLICK",
|
||||
"NNN_SEL",
|
||||
"NNN_ARCHIVE",
|
||||
@@ -850,7 +856,7 @@ static int set_sort_flags(int r);
|
||||
static void statusbar(char *path);
|
||||
static bool get_output(char *file, char *arg1, char *arg2, int fdout, bool page);
|
||||
#ifndef NOFIFO
|
||||
-static void notify_fifo(bool force);
|
||||
+static void notify_fifo(bool force, bool closepreview);
|
||||
#endif
|
||||
|
||||
/* Functions */
|
||||
@@ -3140,7 +3146,7 @@ try_quit:
|
||||
} else {
|
||||
#ifndef NOFIFO
|
||||
if (!g_state.fifomode)
|
||||
- notify_fifo(TRUE); /* Send hovered path to NNN_FIFO */
|
||||
+ notify_fifo(TRUE, FALSE); /* Send hovered path to NNN_FIFO */
|
||||
#endif
|
||||
escaped = TRUE;
|
||||
settimeout();
|
||||
@@ -5258,15 +5264,20 @@ static void run_cmd_as_plugin(const char *file, uchar_t flags)
|
||||
|
||||
static bool plctrl_init(void)
|
||||
{
|
||||
- size_t len;
|
||||
+ size_t len, lenbuf;
|
||||
+ pid_t pid = getpid();
|
||||
|
||||
/* g_tmpfpath is used to generate tmp file names */
|
||||
g_tmpfpath[tmpfplen - 1] = '\0';
|
||||
- len = xstrsncpy(g_pipepath, g_tmpfpath, TMP_LEN_MAX);
|
||||
+ len = lenbuf = xstrsncpy(g_pipepath, g_tmpfpath, TMP_LEN_MAX);
|
||||
g_pipepath[len - 1] = '/';
|
||||
- len = xstrsncpy(g_pipepath + len, "nnn-pipe.", TMP_LEN_MAX - len) + len;
|
||||
- xstrsncpy(g_pipepath + len - 1, xitoa(getpid()), TMP_LEN_MAX - len);
|
||||
+ xstrsncpy(g_ppipepath, g_pipepath, TMP_LEN_MAX);
|
||||
+ len += xstrsncpy(g_pipepath + len, "nnn-pipe.", TMP_LEN_MAX - len);
|
||||
+ xstrsncpy(g_pipepath + len - 1, xitoa(pid), TMP_LEN_MAX - len);
|
||||
+ len = xstrsncpy(g_ppipepath + lenbuf, "nnn-ppipe.", TMP_LEN_MAX - lenbuf) + lenbuf;
|
||||
+ xstrsncpy(g_ppipepath + len - 1, xitoa(pid), TMP_LEN_MAX - len);
|
||||
setenv(env_cfg[NNN_PIPE], g_pipepath, TRUE);
|
||||
+ setenv(env_cfg[NNN_PPIPE], g_ppipepath, TRUE);
|
||||
|
||||
return EXIT_SUCCESS;
|
||||
}
|
||||
@@ -5295,6 +5306,21 @@ static ssize_t read_nointr(int fd, void *buf, size_t count)
|
||||
return len;
|
||||
}
|
||||
|
||||
+void *previewpipe(void *arg __attribute__ ((unused)))
|
||||
+{
|
||||
+ int fd, buf;
|
||||
+
|
||||
+ mkfifo(g_ppipepath, 0600);
|
||||
+ fd = open(g_ppipepath, O_RDONLY);
|
||||
+
|
||||
+ if (read(fd, &buf, 1) == 1)
|
||||
+ g_state.previewer = buf;
|
||||
+
|
||||
+ close(fd);
|
||||
+ unlink(g_ppipepath);
|
||||
+ return NULL;
|
||||
+}
|
||||
+
|
||||
static char *readpipe(int fd, char *ctxnum, char **path)
|
||||
{
|
||||
char ctx, *nextpath = NULL;
|
||||
@@ -5979,7 +6005,7 @@ static void populate(char *path, char *lastname)
|
||||
}
|
||||
|
||||
#ifndef NOFIFO
|
||||
-static void notify_fifo(bool force)
|
||||
+static void notify_fifo(bool force, bool closepreview)
|
||||
{
|
||||
if (!fifopath)
|
||||
return;
|
||||
@@ -5995,6 +6021,12 @@ static void notify_fifo(bool force)
|
||||
}
|
||||
}
|
||||
|
||||
+ if (closepreview) {
|
||||
+ if (write(fifofd, "close\n", 6) != 6)
|
||||
+ xerror();
|
||||
+ return;
|
||||
+ }
|
||||
+
|
||||
static struct entry lastentry;
|
||||
|
||||
if (!force && !memcmp(&lastentry, &pdents[cur], sizeof(struct entry))) // NOLINT
|
||||
@@ -6027,7 +6059,7 @@ static void send_to_explorer(int *presel)
|
||||
if (fd > 1)
|
||||
close(fd);
|
||||
} else
|
||||
- notify_fifo(TRUE); /* Send opened path to NNN_FIFO */
|
||||
+ notify_fifo(TRUE, FALSE); /* Send opened path to NNN_FIFO */
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -6060,7 +6092,7 @@ static void move_cursor(int target, int ignore_scrolloff)
|
||||
|
||||
#ifndef NOFIFO
|
||||
if (!g_state.fifomode)
|
||||
- notify_fifo(FALSE); /* Send hovered path to NNN_FIFO */
|
||||
+ notify_fifo(FALSE, FALSE); /* Send hovered path to NNN_FIFO */
|
||||
#endif
|
||||
}
|
||||
|
||||
@@ -6733,7 +6765,7 @@ static bool browse(char *ipath, const char *session, int pkey)
|
||||
pEntry pent;
|
||||
enum action sel;
|
||||
struct stat sb;
|
||||
- int r = -1, presel, selstartid = 0, selendid = 0;
|
||||
+ int r = -1, presel, selstartid = 0, selendid = 0, previewkey = 0;
|
||||
const uchar_t opener_flags = (cfg.cliopener ? F_CLI : (F_NOTRACE | F_NOSTDIN | F_NOWAIT));
|
||||
bool watch = FALSE, cd = TRUE;
|
||||
ino_t inode = 0;
|
||||
@@ -6991,7 +7023,7 @@ nochange:
|
||||
move_cursor(r, 1);
|
||||
#ifndef NOFIFO
|
||||
else if ((event.bstate == BUTTON1_PRESSED) && !g_state.fifomode)
|
||||
- notify_fifo(TRUE); /* Send clicked path to NNN_FIFO */
|
||||
+ notify_fifo(TRUE, FALSE); /* Send clicked path to NNN_FIFO */
|
||||
#endif
|
||||
/* Handle right click selection */
|
||||
if (event.bstate == BUTTON3_PRESSED) {
|
||||
@@ -7153,7 +7185,14 @@ nochange:
|
||||
&& strstr(g_buf, "text")
|
||||
#endif
|
||||
) {
|
||||
+ if (g_state.previewer)
|
||||
+ notify_fifo(FALSE, TRUE);
|
||||
spawn(editor, newpath, NULL, NULL, F_CLI);
|
||||
+ if (g_state.previewer) {
|
||||
+ pkey = previewkey;
|
||||
+ goto run_plugin;
|
||||
+ }
|
||||
+
|
||||
if (cfg.filtermode) {
|
||||
presel = FILTER;
|
||||
clearfilter();
|
||||
@@ -7471,8 +7510,14 @@ nochange:
|
||||
copycurname();
|
||||
goto nochange;
|
||||
case SEL_EDIT:
|
||||
+ if (g_state.previewer)
|
||||
+ notify_fifo(FALSE, TRUE);
|
||||
if (!(g_state.picker || g_state.fifomode))
|
||||
spawn(editor, newpath, NULL, NULL, F_CLI);
|
||||
+ if (g_state.previewer) {
|
||||
+ pkey = previewkey;
|
||||
+ goto run_plugin;
|
||||
+ }
|
||||
continue;
|
||||
default: /* SEL_LOCK */
|
||||
lock_terminal();
|
||||
@@ -7860,6 +7905,7 @@ nochange:
|
||||
cd = FALSE;
|
||||
goto begin;
|
||||
}
|
||||
+run_plugin:
|
||||
case SEL_PLUGIN:
|
||||
/* Check if directory is accessible */
|
||||
if (!xdiraccess(plgpath)) {
|
||||
@@ -7885,6 +7931,12 @@ nochange:
|
||||
goto nochange;
|
||||
}
|
||||
|
||||
+ if (xstrcmp(tmp, "preview-tui") == 0) {
|
||||
+ previewkey = r;
|
||||
+ pthread_t tid;
|
||||
+ pthread_create(&tid, NULL, previewpipe, NULL);
|
||||
+ }
|
||||
+
|
||||
if (tmp[0] == '-' && tmp[1]) {
|
||||
++tmp;
|
||||
r = FALSE; /* Do not refresh dir after completion */
|
||||
@@ -7943,7 +7995,13 @@ nochange:
|
||||
case SEL_SHELL: // fallthrough
|
||||
case SEL_LAUNCH: // fallthrough
|
||||
case SEL_PROMPT:
|
||||
+ if (g_state.previewer)
|
||||
+ notify_fifo(FALSE, TRUE);
|
||||
r = handle_cmd(sel, path, newpath);
|
||||
+ if (g_state.previewer) {
|
||||
+ pkey = previewkey;
|
||||
+ goto run_plugin;
|
||||
+ }
|
||||
|
||||
/* Continue in type-to-nav mode, if enabled */
|
||||
if (cfg.filtermode)
|
||||
@@ -8492,8 +8550,10 @@ static void cleanup(void)
|
||||
if (g_state.autofifo)
|
||||
unlink(fifopath);
|
||||
#endif
|
||||
- if (g_state.pluginit)
|
||||
+ if (g_state.pluginit){
|
||||
unlink(g_pipepath);
|
||||
+ unlink(g_ppipepath);
|
||||
+ }
|
||||
#ifdef DEBUG
|
||||
disabledbg();
|
||||
#endif
|
||||
@@ -9020,7 +9080,7 @@ int main(int argc, char *argv[])
|
||||
|
||||
#ifndef NOFIFO
|
||||
if (!g_state.fifomode)
|
||||
- notify_fifo(FALSE);
|
||||
+ notify_fifo(FALSE, TRUE);
|
||||
if (fifofd != -1)
|
||||
close(fifofd);
|
||||
#endif
|
|
@ -1,15 +1,17 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: Copy selection to system clipboard as newline-separated entries
|
||||
# Requires: tr and
|
||||
# xclip/xsel (Linux)
|
||||
# pbcopy (macOS)
|
||||
# termux-clipboard-set (Termux)
|
||||
# clip.exe (WSL)
|
||||
# clip (Cygwin)
|
||||
# wl-copy (Wayland)
|
||||
# Dependencies:
|
||||
# - tr
|
||||
# - xclip/xsel (Linux)
|
||||
# - pbcopy (macOS)
|
||||
# - termux-clipboard-set (Termux)
|
||||
# - clip.exe (WSL)
|
||||
# - clip (Cygwin)
|
||||
# - wl-copy (Wayland)
|
||||
# - clipboard (Haiku)
|
||||
#
|
||||
# LIMITATION: breaks if a filename has newline in it
|
||||
# Limitation: breaks if a filename has newline in it
|
||||
#
|
||||
# Note: For a space-separated list:
|
||||
# xargs -0 < "$SELECTION"
|
||||
|
@ -19,27 +21,31 @@
|
|||
|
||||
IFS="$(printf '%b_' '\n')"; IFS="${IFS%_}" # protect trailing \n
|
||||
|
||||
SELECTION=${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.selection
|
||||
selection=${NNN_SEL:-${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.selection}
|
||||
[ -s "$selection" ] || { echo "plugin .cbcp error: empty selection" >&2 ; exit 1; }
|
||||
|
||||
if which xsel >/dev/null 2>&1; then
|
||||
# Linux
|
||||
tr '\0' '\n' < "$SELECTION" | xsel -bi
|
||||
elif which xclip >/dev/null 2>&1; then
|
||||
# Linux
|
||||
tr '\0' '\n' < "$SELECTION" | xclip -sel clip
|
||||
elif which pbcopy >/dev/null 2>&1; then
|
||||
# macOS
|
||||
tr '\0' '\n' < "$SELECTION" | pbcopy
|
||||
elif which termux-clipboard-set >/dev/null 2>&1; then
|
||||
# Termux
|
||||
tr '\0' '\n' < "$SELECTION" | termux-clipboard-set
|
||||
elif which clip.exe >/dev/null 2>&1; then
|
||||
# WSL
|
||||
tr '\0' '\n' < "$SELECTION" | clip.exe
|
||||
elif which clip >/dev/null 2>&1; then
|
||||
# Cygwin
|
||||
tr '\0' '\n' < "$SELECTION" | clip
|
||||
elif which wl-copy >/dev/null 2>&1; then
|
||||
if [ "$XDG_SESSION_TYPE" = "wayland" ]; then
|
||||
# Wayland
|
||||
tr '\0' '\n' < "$SELECTION" | wl-copy
|
||||
tr '\0' '\n' < "$selection" | wl-copy
|
||||
elif type xsel >/dev/null 2>&1; then
|
||||
# Linux
|
||||
tr '\0' '\n' < "$selection" | xsel -bi
|
||||
elif type xclip >/dev/null 2>&1; then
|
||||
# Linux
|
||||
tr '\0' '\n' < "$selection" | xclip -sel clip
|
||||
elif type pbcopy >/dev/null 2>&1; then
|
||||
# macOS
|
||||
tr '\0' '\n' < "$selection" | pbcopy
|
||||
elif type termux-clipboard-set >/dev/null 2>&1; then
|
||||
# Termux
|
||||
tr '\0' '\n' < "$selection" | termux-clipboard-set
|
||||
elif type clip.exe >/dev/null 2>&1; then
|
||||
# WSL
|
||||
tr '\0' '\n' < "$selection" | clip.exe
|
||||
elif type clip >/dev/null 2>&1; then
|
||||
# Cygwin
|
||||
tr '\0' '\n' < "$selection" | clip
|
||||
elif type clipboard >/dev/null 2>&1; then
|
||||
# Haiku
|
||||
tr '\0' '\n' < "$selection" | clipboard --stdin
|
||||
fi
|
||||
|
|
|
@ -0,0 +1,441 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: Print icons in front of list of directories/files
|
||||
|
||||
# Dependencies: awk
|
||||
|
||||
# Usage
|
||||
# 1. Set colors and/or icons to your liking
|
||||
# 2. Pipe any directory listing to iconlookup and it will output prepended icons
|
||||
# 3. preview-tui uses the script to prepend icon to directory listings
|
||||
# 4. Aditionally you can consider adding it to your PATH and/or FZF_DEFAULT_COMMAND to
|
||||
# make it work with various fzf plugins (make sure you also add --ansi to your FZF_DEFAULT_OPTS)
|
||||
|
||||
# Shell: POSIX compliant
|
||||
|
||||
# Author: Luuk van Baal (https://github.com/luukvbaal/iconlookup)
|
||||
|
||||
icon_lookup() {
|
||||
awk 'BEGIN {
|
||||
# Set your ANSI colorscheme below (https://en.wikipedia.org/wiki/ANSI_escape_code#Colors).
|
||||
# Default uses standard nnn icon colors, 8 and 24-bit nord themes are commented out.
|
||||
colordepth=8 #colordepth=8 #colordepth=24
|
||||
color_dirtxt=39 #color_dirtxt=111 #color_dirtxt="129;161;193"
|
||||
color_filetxt=15 #color_filetxt=111 #color_filetxt="129;161;193"
|
||||
color_default=39 #color_default=111 #color_default="129;161;193"
|
||||
color_video=93 #color_video=110 #color_video="136;192;208"
|
||||
color_audio=220 #color_audio=150 #color_audio="163;190;140"
|
||||
color_image=82 #color_image=150 #color_image="163;190;140"
|
||||
color_docs=202 #color_docs=173 #color_docs="208;135;112"
|
||||
color_archive=209 #color_archive=179 #color_archive="235;203;139"
|
||||
color_c=81 #color_c=150 #color_c="163;190;140"
|
||||
color_elixir=104 #color_elixir=109 #color_elixir="143;188;187"
|
||||
color_java=32 #color_java=139 #color_java="180;142;173"
|
||||
color_js=47 #color_js=109 #color_js="143;188;187"
|
||||
color_react=39 #color_react=111 #color_react="129;161;193"
|
||||
color_css=199 #color_css=110 #color_css="136;192;208"
|
||||
color_python=227 #color_python=68 #color_python="94;129;172"
|
||||
color_lua=19 #color_lua=167 #color_lua="191;97;106"
|
||||
color_document=15 #color_document=173 #color_document="208;135;112"
|
||||
color_fsharp=31 #color_fsharp=179 #color_fsharp="180;142;173"
|
||||
color_ruby=160 #color_ruby=150 #color_ruby="163;190;140"
|
||||
color_scala=196 #color_scala=139 #color_scala="143;188;187"
|
||||
color_shell=47 #color_shell=109 #color_shell="143;188;187"
|
||||
color_vim=28 #color_vim=109 #color_vim="143;188;187"
|
||||
|
||||
# icons[][1] contains icon and icons[][2] contains color
|
||||
icons["directory"][1] = ""; icons["directory"][2] = color_default
|
||||
icons["file"][1] = ""; icons["file"][2] = color_default
|
||||
icons["exec"][1] = ""; icons["exec"][2] = color_default
|
||||
icons["manual"][1] = ""; icons["manual"][2] = color_docs
|
||||
icons["pipe"][1] = ""; icons["pipe"][2] = color_default
|
||||
icons["socket"][1] = ""; icons["socket"][2] = color_default
|
||||
icons["door"][1] = "➡"; icons["door"][2] = color_default
|
||||
|
||||
# top level and common icons
|
||||
icons[".git"][1] = ""; icons[".git"][2] = color_default
|
||||
icons["desktop"][1] = ""; icons["desktop"][2] = color_default
|
||||
icons["briefcase"][1] = ""; icons["briefcase"][2] = color_default
|
||||
icons["document"][1] = ""; icons["document"][2] = color_default
|
||||
icons["downloads"][1] = ""; icons["downloads"][2] = color_default
|
||||
icons["music"][1] = ""; icons["music"][2] = color_default
|
||||
icons["musicfile"][1] = ""; icons["musicfile"][2] = color_audio
|
||||
icons["pictures"][1] = ""; icons["pictures"][2] = color_default
|
||||
icons["picturefile"][1] = ""; icons["picturefile"][2] = color_image
|
||||
icons["public"][1] = ""; icons["public"][2] = color_default
|
||||
icons["templates"][1] = ""; icons["templates"][2] = color_default
|
||||
icons["videos"][1] = ""; icons["videos"][2] = color_default
|
||||
icons["videofile"][1] = ""; icons["videofile"][2] = color_video
|
||||
icons["changelog"][1] = ""; icons["changelog"][2] = color_docs
|
||||
icons["configure"][1] = ""; icons["configure"][2] = color_default
|
||||
icons["license"][1] = ""; icons["license"][2] = color_docs
|
||||
icons["makefile"][1] = ""; icons["makefile"][2] = color_default
|
||||
icons["archive"][1] = ""; icons["archive"][2] = color_archive
|
||||
icons["rust"][1] = ""; icons["rust"][2] = color_default
|
||||
icons["script"][1] = ""; icons["script"][2] = color_shell
|
||||
icons["subtitle"][1] = ""; icons["subtitle"][2] = color_default
|
||||
icons["cplusplus"][1] = ""; icons["cplusplus"][2] = color_c
|
||||
icons["java"][1] = ""; icons["java"][2] = color_java
|
||||
icons["clojure"][1] = ""; icons["clojure"][2] = color_default
|
||||
icons["js"][1] = ""; icons["js"][2] = color_js
|
||||
icons["linux"][1] = ""; icons["linux"][2] = color_default
|
||||
icons["elixir"][1] = ""; icons["elixir"][2] = color_fsharp
|
||||
icons["fsharp"][1] = ""; icons["fsharp"][2] = color_fsharp
|
||||
icons["ruby"][1] = ""; icons["ruby"][2] = color_ruby
|
||||
icons["c"][1] = ""; icons["c"][2] = color_c
|
||||
icons["chess"][1] = ""; icons["chess"][2] = color_default
|
||||
icons["haskell"][1] = ""; icons["haskell"][2] = color_vim
|
||||
icons["font"][1] = ""; icons["font"][2] = color_default
|
||||
icons["html"][1] = ""; icons["html"][2] = color_default
|
||||
icons["react"][1] = ""; icons["react"][2] = color_react
|
||||
icons["python"][1] = ""; icons["python"][2] = color_python
|
||||
icons["database"][1] = ""; icons["database"][2] = color_default
|
||||
icons["worddoc"][1] = ""; icons["worddoc"][2] = color_document
|
||||
icons["playlist"][1] = ""; icons["playlist"][2] = color_audio
|
||||
icons["opticaldisk"][1] = ""; icons["opticaldisk"][2] = color_archive
|
||||
|
||||
# numbers
|
||||
icons["1"][1] = icons["manual"][1]; icons["1"][2] = icons["manual"][2]
|
||||
icons["7z"][1] = icons["archive"][1]; icons["7z"][2] = icons["archive"][2]
|
||||
|
||||
# a
|
||||
icons["a"][1] = icons["manual"][1]; icons["a"][2] = icons["manual"][2]
|
||||
icons["apk"][1] = icons["archive"][1]; icons["apk"][2] = icons["archive"][2]
|
||||
icons["asm"][1] = icons["file"][1]; icons["asm"][2] = icons["file"][2]
|
||||
icons["aup"][1] = icons["musicfile"][1]; icons["aup"][2] = icons["musicfile"][2]
|
||||
icons["avi"][1] = icons["videofile"][1]; icons["avi"][2] = icons["videofile"][2]
|
||||
|
||||
# b
|
||||
icons["bat"][1] = icons["script"][1]; icons["bat"][2] = icons["script"][2]
|
||||
icons["bin"][1] = ""; icons["bin"][2] = color_default
|
||||
icons["bmp"][1] = icons["picturefile"][1]; icons["bmp"][2] = icons["picturefile"][2]
|
||||
icons["bz2"][1] = icons["archive"][1]; icons["bz2"][2] = icons["archive"][2]
|
||||
|
||||
# c
|
||||
icons["cplusplus"][1] = icons["cplusplus"][1]; icons["cplusplus"][2] = icons["cplusplus"][2]
|
||||
icons["cabal"][1] = icons["haskell"][1]; icons["cab"][2] = icons["haskell"][2]
|
||||
icons["cab"][1] = icons["archive"][1]; icons["cab"][2] = icons["archive"][2]
|
||||
icons["cbr"][1] = icons["archive"][1]; icons["cbr"][2] = icons["archive"][2]
|
||||
icons["cbz"][1] = icons["archive"][1]; icons["cbz"][2] = icons["archive"][2]
|
||||
icons["cc"][1] = icons["cplusplus"][1]; icons["cc"][2] = icons["cplusplus"][2]
|
||||
icons["class"][1] = icons["java"][1]; icons["class"][2] = icons["java"][2]
|
||||
icons["clj"][1] = icons["clojure"][1]; icons["clj"][2] = icons["clojure"][2]
|
||||
icons["cljc"][1] = icons["clojure"][1]; icons["cljc"][2] = icons["clojure"][2]
|
||||
icons["cljs"][1] = icons["clojure"][1]; icons["cljs"][2] = icons["clojure"][2]
|
||||
icons["cmake"][1] = icons["makefile"][1]; icons["cmake"][2] = icons["makefile"][2]
|
||||
icons["coffee"][1] = ""; icons["coffee"][2] = color_default
|
||||
icons["conf"][1] = icons["configure"][1]; icons["conf"][2] = icons["configure"][2]
|
||||
icons["cpio"][1] = icons["archive"][1]; icons["cpio"][2] = icons["archive"][2]
|
||||
icons["cpp"][1] = icons["cplusplus"][1]; icons["cpp"][2] = icons["cplusplus"][2]
|
||||
icons["css"][1] = ""; icons["css"][2] = color_css
|
||||
icons["cue"][1] = icons["playlist"][1]; icons["cue"][2] = icons["playlist"][2]
|
||||
icons["cvs"][1] = icons["configure"][1]; icons["cvs"][2] = icons["configure"][2]
|
||||
icons["cxx"][1] = icons["cplusplus"][1]; icons["cxx"][2] = icons["cplusplus"][2]
|
||||
|
||||
# d
|
||||
icons["db"][1] = icons["database"][1]; icons["db"][2] = icons["database"][2]
|
||||
icons["deb"][1] = ""; icons["deb"][2] = color_archive
|
||||
icons["diff"][1] = ""; icons["diff"][2] = color_default
|
||||
icons["dll"][1] = icons["script"][1]; icons["dll"][2] = icons["script"][2]
|
||||
icons["doc"][1] = icons["worddoc"][1]; icons["doc"][2] = icons["worddoc"][2]
|
||||
icons["docx"][1] = icons["worddoc"][1]; icons["docx"][2] = icons["worddoc"][2]
|
||||
|
||||
# e
|
||||
icons["ejs"][1] = icons["js"][1]; icons["ejs"][2] = icons["js"][2]
|
||||
icons["elf"][1] = icons["linux"][1]; icons["elf"][2] = icons["linux"][2]
|
||||
icons["epub"][1] = icons["manual"][1]; icons["epub"][2] = icons["manual"][2]
|
||||
icons["exe"][1] = icons["exec"][1]; icons["exe"][2] = icons["exec"][2]
|
||||
icons["ex"][1] = icons["elixir"][1]; icons["ex"][2] = icons["elixir"][2]
|
||||
icons["eex"][1] = icons["elixir"][1]; icons["eex"][2] = icons["elixir"][2]
|
||||
icons["exs"][1] = icons["elixir"][1]; icons["exs"][2] = icons["elixir"][2]
|
||||
|
||||
# f
|
||||
icons["fsharp"][1] = icons["fsharp"][1]; icons["fsharp"][2] = icons["fsharp"][2]
|
||||
icons["flac"][1] = icons["musicfile"][1]; icons["flac"][2] = icons["musicfile"][2]
|
||||
icons["fen"][1] = icons["chess"][1]; icons["fen"][2] = icons["chess"][2]
|
||||
icons["flv"][1] = icons["videofile"][1]; icons["flv"][2] = icons["videofile"][2]
|
||||
icons["fs"][1] = icons["fsharp"][1]; icons["fs"][2] = icons["fsharp"][2]
|
||||
icons["fsi"][1] = icons["fsharp"][1]; icons["fsi"][2] = icons["fsharp"][2]
|
||||
icons["fsscript"][1] = icons["fsharp"][1]; icons["fsscript"][2] = icons["fsharp"][2]
|
||||
icons["fsx"][1] = icons["fsharp"][1]; icons["fsx"][2] = icons["fsharp"][2]
|
||||
|
||||
# g
|
||||
icons["gem"][1] = icons["ruby"][1]; icons["gem"][2] = icons["ruby"][2]
|
||||
icons["gif"][1] = icons["picturefile"][1]; icons["gif"][2] = icons["picturefile"][2]
|
||||
icons["go"][1] = ""; icons["go"][2] = color_default
|
||||
icons["gz"][1] = icons["archive"][1]; icons["gz"][2] = icons["archive"][2]
|
||||
icons["gzip"][1] = icons["archive"][1]; icons["gzip"][2] = icons["archive"][2]
|
||||
|
||||
# h
|
||||
icons["h"][1] = icons["c"][1]; icons["h"][2] = icons["c"][2]
|
||||
icons["hh"][1] = icons["cplusplus"][1]; icons["hh"][2] = icons["cplusplus"][2]
|
||||
icons["hpp"][1] = icons["cplusplus"][1]; icons["hpp"][2] = icons["cplusplus"][2]
|
||||
icons["hs"][1] = icons["haskell"][1]; icons["hs"][2] = icons["haskell"][2]
|
||||
icons["htaccess"][1] = icons["configure"][1]; icons["htaccess"][2] = icons["configure"][2]
|
||||
icons["htpasswd"][1] = icons["configure"][1]; icons["htpasswd"][2] = icons["configure"][2]
|
||||
icons["htm"][1] = icons["html"][1]; icons["htm"][2] = icons["html"][2]
|
||||
icons["hxx"][1] = icons["cplusplus"][1]; icons["hxx"][2] = icons["cplusplus"][2]
|
||||
icons["heex"][1] = icons["elixir"][1]; icons["heex"][2] = icons["elixir"][2]
|
||||
|
||||
# i
|
||||
icons["ico"][1] = icons["picturefile"][1]; icons["ico"][2] = icons["picturefile"][2]
|
||||
icons["img"][1] = icons["opticaldisk"][1]; icons["img"][2] = icons["opticaldisk"][2]
|
||||
icons["ini"][1] = icons["configure"][1]; icons["ini"][2] = icons["configure"][2]
|
||||
icons["iso"][1] = icons["opticaldisk"][1]; icons["iso"][2] = icons["opticaldisk"][2]
|
||||
icons["isub"][1] = icons["subtitle"][1]; icons["isub"][2] = icons["subtitle"][2]
|
||||
|
||||
# j
|
||||
icons["jar"][1] = icons["java"][1]; icons["jar"][2] = icons["java"][2]
|
||||
icons["java"][1] = icons["java"][1]; icons["java"][2] = icons["java"][2]
|
||||
icons["jl"][1] = icons["configure"][1]; icons["jl"][2] = icons["configure"][2]
|
||||
icons["jpeg"][1] = icons["picturefile"][1]; icons["jpeg"][2] = icons["picturefile"][2]
|
||||
icons["jpg"][1] = icons["picturefile"][1]; icons["jpg"][2] = icons["picturefile"][2]
|
||||
icons["json"][1] = ""; icons["json"][2] = color_js
|
||||
icons["jsx"][1] = icons["react"][1]; icons["jsx"][2] = icons["react"][2]
|
||||
icons["jxl"][1] = icons["picturefile"][1]; icons["jxl"][2] = icons["picturefile"][2]
|
||||
|
||||
# k
|
||||
icons["ksh"][1] = icons["font"][1]; icons["ksf"][2] = icons["font"][2]
|
||||
|
||||
# l
|
||||
icons["lha"][1] = icons["archive"][1]; icons["lha"][2] = icons["archive"][2]
|
||||
icons["lhs"][1] = icons["haskell"][1]; icons["lhs"][2] = icons["haskell"][2]
|
||||
icons["ilog"][1] = icons["document"][1]; icons["ilog"][2] = icons["document"][2]
|
||||
icons["lua"][1] = ""; icons["lua"][2] = color_lua
|
||||
icons["lzh"][1] = icons["archive"][1]; icons["lzh"][2] = icons["archive"][2]
|
||||
icons["lzma"][1] = icons["archive"][1]; icons["lzma"][2] = icons["archive"][2]
|
||||
|
||||
# m
|
||||
icons["m"][1] = ""; icons["mat"][2] = color_c
|
||||
icons["m4a"][1] = icons["musicfile"][1]; icons["m4a"][2] = icons["musicfile"][2]
|
||||
icons["m4v"][1] = icons["videofile"][1]; icons["m4v"][2] = icons["videofile"][2]
|
||||
icons["mat"][1] = ""; icons["mat"][2] = color_c
|
||||
icons["markdown"][1] = ""; icons["markdown"][2] = color_docs
|
||||
icons["md"][1] = ""; icons["md"][2] = color_docs
|
||||
icons["mk"][1] = icons["makefile"][1]; icons["mk"][2] = icons["makefile"][2]
|
||||
icons["mkv"][1] = icons["videofile"][1]; icons["mkv"][2] = icons["videofile"][2]
|
||||
icons["mov"][1] = icons["videofile"][1]; icons["mov"][2] = icons["videofile"][2]
|
||||
icons["mp3"][1] = icons["musicfile"][1]; icons["mp3"][2] = icons["musicfile"][2]
|
||||
icons["mp4"][1] = icons["videofile"][1]; icons["mp4"][2] = icons["videofile"][2]
|
||||
icons["mpeg"][1] = icons["videofile"][1]; icons["mpeg"][2] = icons["videofile"][2]
|
||||
icons["mpg"][1] = icons["videofile"][1]; icons["mpg"][2] = icons["videofile"][2]
|
||||
icons["msi"][1] = ""; icons["msi"][2] = color_default
|
||||
|
||||
# n
|
||||
icons["nix"][1] = ""; icons["nix"][2] = color_fsharp
|
||||
|
||||
# o
|
||||
icons["o"][1] = icons["manual"][1]; icons["o"][2] = icons["manual"][2]
|
||||
icons["ogg"][1] = icons["musicfile"][1]; icons["ogg"][2] = icons["musicfile"][2]
|
||||
icons["odownload"][1] = icons["download"][1]; icons["odownload"][2] = icons["download"][2]
|
||||
icons["otf"][1] = icons["font"][1]; icons["otf"][2] = icons["font"][2]
|
||||
icons["out"][1] = icons["linux"][1]; icons["out"][2] = icons["linux"][2]
|
||||
|
||||
# p
|
||||
icons["part"][1] = icons["download"][1]; icons["part"][2] = icons["download"][2]
|
||||
icons["patch"][1] = icons["diff"][1]; icons["patch"][2] = icons["diff"][2]
|
||||
icons["pdf"][1] = ""; icons["pdf"][2] = color_docs
|
||||
icons["pgn"][1] = icons["chess"][1]; icons["pgn"][2] = icons["chess"][2]
|
||||
icons["php"][1] = ""; icons["php"][2] = color_default
|
||||
icons["png"][1] = icons["picturefile"][1]; icons["png"][2] = icons["picturefile"][2]
|
||||
icons["ppt"][1] = ""; icons["ppt"][2] = color_default
|
||||
icons["pptx"][1] = ""; icons["pptx"][2] = color_default
|
||||
icons["psb"][1] = ""; icons["psb"][2] = color_default
|
||||
icons["psd"][1] = ""; icons["psd"][2] = color_default
|
||||
icons["py"][1] = icons["python"][1]; icons["py"][2] = icons["python"][2]
|
||||
icons["pyc"][1] = icons["python"][1]; icons["pyc"][2] = icons["python"][2]
|
||||
icons["pyd"][1] = icons["python"][1]; icons["pyd"][2] = icons["python"][2]
|
||||
icons["pyo"][1] = icons["python"][1]; icons["pyo"][2] = icons["python"][2]
|
||||
|
||||
# q
|
||||
|
||||
# r
|
||||
icons["rar"][1] = icons["archive"][1]; icons["rar"][2] = icons["archive"][2]
|
||||
icons["rc"][1] = icons["configure"][1]; icons["rc"][2] = icons["configure"][2]
|
||||
icons["rom"][1] = ""; icons["rom"][2] = color_default
|
||||
icons["rpm"][1] = icons["archive"][1]; icons["rpm"][2] = icons["archive"][2]
|
||||
icons["rss"][1] = ""; icons["rss"][2] = color_default
|
||||
icons["rtf"][1] = ""; icons["rtf"][2] = color_default
|
||||
|
||||
# s
|
||||
icons["sass"][1] = ""; icons["sass"][2] = color_css
|
||||
icons["scss"][1] = ""; icons["scss"][2] = color_css
|
||||
icons["so"][1] = icons["manual"][1]; icons["so"][2] = icons["manual"][2]
|
||||
icons["scala"][1] = ""; icons["scala"][2] = color_scala
|
||||
icons["sh"][1] = icons["script"][1]; icons["sh"][2] = icons["script"][2]
|
||||
icons["slim"][1] = icons["script"][1]; icons["slim"][2] = icons["script"][2]
|
||||
icons["sln"][1] = ""; icons["sln"][2] = color_default
|
||||
icons["sql"][1] = icons["database"][1]; icons["sql"][2] = icons["database"][2]
|
||||
icons["srt"][1] = icons["subtitle"][1]; icons["srt"][2] = icons["subtitle"][2]
|
||||
icons["svg"][1] = icons["picturefile"][1]; icons["svg"][2] = icons["picturefile"][2]
|
||||
|
||||
# t
|
||||
icons["tar"][1] = icons["archive"][1]; icons["tar"][2] = icons["archive"][2]
|
||||
icons["tex"][1] = ""; icons["tex"][2] = color_default
|
||||
icons["tgz"][1] = icons["archive"][1]; icons["tgz"][2] = icons["archive"][2]
|
||||
icons["ts"][1] = ""; icons["ts"][2] = color_js
|
||||
icons["tsx"][1] = icons["react"][1]; icons["tsx"][2] = icons["react"][2]
|
||||
icons["txt"][1] = icons["document"][1]; icons["txt"][2] = icons["document"][2]
|
||||
icons["txz"][1] = icons["archive"][1]; icons["txz"][2] = icons["archive"][2]
|
||||
icons["ttf"][1] = icons["font"][1]; icons["ttf"][2] = icons["font"][2]
|
||||
|
||||
# u
|
||||
|
||||
# v
|
||||
icons["vid"][1] = icons["videofile"][1]; icons["vid"][2] = icons["videofile"][2]
|
||||
icons["vim"][1] = ""; icons["vim"][2] = color_vim
|
||||
icons["vimrc"][1] = ""; icons["vimrc"][2] = color_vim
|
||||
icons["vtt"][1] = icons["subtitle"][1]; icons["vtt"][2] = icons["subtitle"][2]
|
||||
# w
|
||||
icons["wav"][1] = icons["musicfile"][1]; icons["wav"][2] = icons["musicfile"][2]
|
||||
icons["webm"][1] = icons["videofile"][1]; icons["webm"][2] = icons["videofile"][2]
|
||||
icons["wma"][1] = icons["videofile"][1]; icons["wma"][2] = icons["videofile"][2]
|
||||
icons["wmv"][1] = icons["videofile"][1]; icons["wmv"][2] = icons["videofile"][2]
|
||||
|
||||
# x
|
||||
icons["xbps"][1] = icons["archive"][1]; icons["xbps"][2] = color_archive
|
||||
icons["xcf"][1] = icons["picturefile"][1]; icons["xcf"][2] = color_image
|
||||
icons["xhtml"][1] = icons["html"][1]; icons["xhtml"][2] = icons["html"][2]
|
||||
icons["xls"][1] = ""; icons["xls"][2] = color_default
|
||||
icons["xlsx"][1] = ""; icons["xlsx"][2] = color_default
|
||||
icons["xml"][1] = icons["html"][1]; icons["xml"][2] = icons["html"][2]
|
||||
icons["xz"][1] = icons["archive"][1]; icons["xz"][2] = icons["archive"][2]
|
||||
|
||||
# y
|
||||
icons["yaml"][1] = icons["configure"][1]; icons["yaml"][2] = icons["configure"][2]
|
||||
icons["yml"][1] = icons["configure"][1]; icons["yml"][2] = icons["configure"][2]
|
||||
# z
|
||||
icons["zip"][1] = icons["archive"][1]; icons["zip"][2] = icons["archive"][2]
|
||||
icons["zsh"][1] = icons["script"][1]; icons["zsh"][2] = icons["script"][2]
|
||||
icons["zst"][1] = icons["archive"][1]; icons["zst"][2] = icons["archive"][2]
|
||||
|
||||
FS = "."
|
||||
limit = ENVIRON["limit"]
|
||||
switch (colordepth) {
|
||||
case "4":
|
||||
escape="\033["
|
||||
break;
|
||||
case "8":
|
||||
escape="\033[38;5;"
|
||||
break;
|
||||
case "24":
|
||||
escape="\033[38;2;"
|
||||
break;
|
||||
}
|
||||
bstr = ENVIRON["beforestr"]
|
||||
}
|
||||
{
|
||||
# dont print cwd . and leading ./ from tree -f
|
||||
if ($0 ~/^\.$/)
|
||||
next
|
||||
ent = ($0 ~/^\.\//) ? substr($0, 3, length($0) - 2) : $0
|
||||
ext = $NF
|
||||
|
||||
# Print icons, set color and bold directories by using ansi escape codes
|
||||
if (ext in icons)
|
||||
printcolor(icons[ext][1], icons[ext][2], color_filetxt, ent, "10")
|
||||
else
|
||||
switch (substr(ent, length(ent), 1)) {
|
||||
case "/":
|
||||
printcolor(icons["directory"][1], color_default, color_dirtxt, ent, "1")
|
||||
break;
|
||||
case "*":
|
||||
printcolor(icons["exe"][1], color_default, color_filetxt, ent, "10")
|
||||
break;
|
||||
case "|":
|
||||
printcolor(icons["pipe"][1], color_default, color_filetxt, ent, "10")
|
||||
break;
|
||||
case "=":
|
||||
printcolor(icons["socket"][1], color_default, color_filetxt, ent, "10")
|
||||
break;
|
||||
case ">":
|
||||
printcolor(icons["door"][1], color_default, color_filetxt, ent, "10")
|
||||
break;
|
||||
default:
|
||||
printcolor(icons["file"][1], color_default, color_filetxt, ent, "10")
|
||||
}
|
||||
}
|
||||
function printcolor(i, c, d, n, b) {
|
||||
if (limit != "" && length(n) + 2 > limit)
|
||||
n = substr(n, 1, limit - 2)
|
||||
printf "\033[0m"
|
||||
printf "%s%s%s;%sm%s %s%sm%s\n", bstr, escape, c, b, i, escape, d, n
|
||||
}'
|
||||
printf '\033[0m'
|
||||
}
|
||||
|
||||
print_begin() {
|
||||
printf '%s\n' "$1" | sed 's/\\n/\n/g'
|
||||
}
|
||||
|
||||
print_end() {
|
||||
printf '%s\n' "$1" | sed 's/\\n/\n/g'
|
||||
}
|
||||
|
||||
print_help() {
|
||||
printf 'Icon Lookup\n
|
||||
Usage:
|
||||
iconlookup [options]
|
||||
iconlookup [-bBe] [string]
|
||||
iconlookup -l [number]
|
||||
iconlookup (-h | --help)
|
||||
|
||||
Prepend icons to list of files based on extension or appended indicator by ls/tree "-F" flag ("/" for directory, "*" for executable etc.)
|
||||
|
||||
Options:
|
||||
-h --help -? Show this screen.
|
||||
-b --before Prepend str before icon.
|
||||
-B --begin Prepend str before output.
|
||||
-e --end Append str after output.
|
||||
-l --limit Limit line length to [number] characters.'
|
||||
}
|
||||
|
||||
while :; do
|
||||
case $1 in
|
||||
-h|-\?|--help)
|
||||
print_help
|
||||
exit ;;
|
||||
-B|--begin)
|
||||
if [ -n "$2" ]; then
|
||||
print_begin "$2"
|
||||
fi
|
||||
shift ;;
|
||||
-e|--end)
|
||||
if [ -n "$2" ]; then
|
||||
end=1
|
||||
endstr="$2"
|
||||
fi
|
||||
shift ;;
|
||||
-b|--before)
|
||||
if [ -n "$2" ]; then
|
||||
export beforestr="$2"
|
||||
fi
|
||||
shift ;;
|
||||
-l|--limit)
|
||||
if [ -n "$2" ]; then
|
||||
export limit="$2"
|
||||
shift
|
||||
else
|
||||
printf 'ERROR: "--limit" requires a non-empty option argument.\n'
|
||||
exit
|
||||
fi ;;
|
||||
--)
|
||||
shift
|
||||
break ;;
|
||||
-?*)
|
||||
printf 'WARNING: Unknown option ignored: %s\n' "$1" ;;
|
||||
*) break ;;
|
||||
esac
|
||||
shift
|
||||
done
|
||||
|
||||
if [ ! -t 0 ]; then
|
||||
[ -n "$beforestr" ] && limit="$((limit - ${#beforestr}))"
|
||||
icon_lookup
|
||||
else
|
||||
printf 'ERROR: no data provided...\nExpecting a directory listing in stdin\n'
|
||||
fi
|
||||
|
||||
if [ -n "$end" ]; then
|
||||
print_end "$endstr"
|
||||
fi
|
|
@ -0,0 +1,174 @@
|
|||
#!/usr/bin/env bash
|
||||
|
||||
# Description: An almost fully POSIX compliant batch file renamer
|
||||
#
|
||||
# Note: nnn auto-detects and invokes this plugin if available
|
||||
# Whitespace is used as delimiter for read.
|
||||
# The plugin doesn't support filenames with leading or trailing whitespace
|
||||
# To use NNN_LIST your shell must support readlink(1)
|
||||
#
|
||||
# Capabilities:
|
||||
# 1. Basic file rename
|
||||
# 2. Detects order change
|
||||
# 3. Can move files
|
||||
# 4. Can remove files
|
||||
# 5. Switch number pairs to swap filenames
|
||||
#
|
||||
# Shell: bash
|
||||
# Author: KlzXS
|
||||
|
||||
# shellcheck disable=SC1090,SC1091
|
||||
. "$(dirname "$0")"/.nnn-plugin-helper
|
||||
|
||||
EDITOR="${EDITOR:-vi}"
|
||||
TMPDIR="${TMPDIR:-/tmp}"
|
||||
NNN_INCLUDE_HIDDEN="${NNN_INCLUDE_HIDDEN:-0}"
|
||||
VERBOSE="${VERBOSE:-0}"
|
||||
RECURSIVE="${RECURSIVE:-0}"
|
||||
|
||||
case "$NNN_TRASH" in
|
||||
1)
|
||||
RM_UTIL="trash-put" ;;
|
||||
2)
|
||||
RM_UTIL="gio trash" ;;
|
||||
*)
|
||||
RM_UTIL="rm -ri --" ;;
|
||||
esac
|
||||
|
||||
exit_status=0
|
||||
|
||||
if nnn_use_selection "Rename"; then
|
||||
# shellcheck disable=SC2154
|
||||
arr=$(tr '\0' '\n' < "$selection")
|
||||
else
|
||||
findcmd="find . ! -name ."
|
||||
|
||||
if [ "$RECURSIVE" -eq 0 ]; then
|
||||
findcmd="$findcmd -prune"
|
||||
fi
|
||||
|
||||
if [ "$NNN_INCLUDE_HIDDEN" -eq 0 ]; then
|
||||
findcmd="$findcmd ! -name \".*\""
|
||||
fi
|
||||
|
||||
if [ -z "$NNN_LIST" ]; then
|
||||
findcmd="$findcmd -print"
|
||||
else
|
||||
findcmd="$findcmd -printf "'"'"$NNN_LIST/%P\n"'"'
|
||||
fi
|
||||
|
||||
arr=$(eval "$findcmd" | sort)
|
||||
fi
|
||||
|
||||
lines=$(printf "%s\n" "$arr" | wc -l)
|
||||
width=${#lines}
|
||||
|
||||
dst_file=$(mktemp "$TMPDIR/.nnnXXXXXX")
|
||||
trap 'rm -f -- "$dst_file"' EXIT
|
||||
|
||||
printf "%s" "$arr" | awk '{printf("%'"${width}"'d %s\n", NR, $0)}' > "$dst_file"
|
||||
|
||||
items=("~")
|
||||
while IFS='' read -r line; do
|
||||
if [ -n "$NNN_LIST" ]; then
|
||||
line=$(readlink "$line" || printf "%s" "$line")
|
||||
fi
|
||||
|
||||
items+=("$line");
|
||||
done < <(printf "%s\n" "$arr")
|
||||
|
||||
$EDITOR "$dst_file"
|
||||
|
||||
while read -r num name; do
|
||||
if [ -z "$name" ]; then
|
||||
if [ -z "$num" ]; then
|
||||
continue
|
||||
fi
|
||||
|
||||
printf "%s: unable to parse line, aborting\n" "$0"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
# check if $num is an integer
|
||||
if [ ! "$num" -eq "$num" ] 2> /dev/null; then
|
||||
printf "%s: unable to parse line, aborting\n" "$0"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
src=${items[$num]}
|
||||
|
||||
if [ -z "$src" ]; then
|
||||
printf "%s: unknown item number %s\n" "$0" "$num" > /dev/stderr
|
||||
continue
|
||||
elif [ "$name" != "$src" ]; then
|
||||
if [ -z "$name" ]; then
|
||||
continue
|
||||
fi
|
||||
|
||||
if [ ! -e "$src" ] && [ ! -L "$src" ]; then
|
||||
printf "%s: %s does not exit\n" "$0" "$src" > /dev/stderr
|
||||
|
||||
unset "items[$num]"
|
||||
continue
|
||||
fi
|
||||
|
||||
# handle swaps
|
||||
if [ -e "$name" ] || [ -L "$name" ]; then
|
||||
tmp="$name~"
|
||||
c=0
|
||||
|
||||
while [ -e "$tmp" ] || [ -L "$tmp" ]; do
|
||||
c=$((c+1))
|
||||
tmp="$tmp~$c"
|
||||
done
|
||||
|
||||
if mv -- "$name" "$tmp"; then
|
||||
if [ "$VERBOSE" -ne 0 ]; then
|
||||
printf "'%s' -> '%s'\n" "$name" "$tmp"
|
||||
fi
|
||||
else
|
||||
printf "%s: failed to rename %s to %s: %s\n" "$0" "$name" "$tmp" "$!" > /dev/stderr
|
||||
exit_status=1
|
||||
fi
|
||||
|
||||
for key in "${!items[@]}"; do
|
||||
if [ "${items[$key]}" = "$name" ]; then
|
||||
items[$key]="$tmp"
|
||||
fi
|
||||
done
|
||||
fi
|
||||
|
||||
dir=$(dirname "$name")
|
||||
if [ ! -d "$dir" ] && ! mkdir -p "$dir"; then
|
||||
printf "%s: failed to create directory tree %s\n" "$0" "$dir" > /dev/stderr
|
||||
exit_status=1
|
||||
elif ! mv -i -- "$src" "$name"; then
|
||||
printf "%s: failed to rename %s to %s: %s\n" "$0" "$name" "$tmp" "$!" > /dev/stderr
|
||||
exit_status=1
|
||||
else
|
||||
if [ -d "$name" ]; then
|
||||
for key in "${!items[@]}"; do
|
||||
items[$key]=$(printf "%s" "${items[$key]}" | sed "s|^$src\(\$\|\/\)|$name\1|")
|
||||
done
|
||||
|
||||
if [ "$VERBOSE" -ne 0 ]; then
|
||||
printf "'%s' => '%s'\n" "$src" "$name"
|
||||
fi
|
||||
else
|
||||
true
|
||||
if [ "$VERBOSE" -ne 0 ]; then
|
||||
printf "'%s' -> '%s'\n" "$src" "$name"
|
||||
fi
|
||||
fi
|
||||
fi
|
||||
fi
|
||||
|
||||
unset "items[$num]"
|
||||
done <"$dst_file"
|
||||
|
||||
unset "items[0]"
|
||||
for item in "${items[@]}"; do
|
||||
$RM_UTIL "$item"
|
||||
done
|
||||
|
||||
exit $exit_status
|
|
@ -5,13 +5,20 @@
|
|||
# Shell: POSIX compliant
|
||||
# Author: Anna Arad
|
||||
|
||||
selection=${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.selection
|
||||
selection=${NNN_SEL:-${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.selection}
|
||||
export selection
|
||||
|
||||
## Set CUR_CTX to 1 to open directory in current context
|
||||
CUR_CTX=0
|
||||
export CUR_CTX
|
||||
|
||||
NNN_PREFER_SELECTION="${NNN_PREFER_SELECTION:-0}"
|
||||
export NNN_PREFER_SELECTION
|
||||
|
||||
## Ask nnn to switch to directory $1 in context $2.
|
||||
## If $2 is not provided, the function asks explicitly.
|
||||
nnn_cd () {
|
||||
dir=$1
|
||||
dir="$1"
|
||||
|
||||
if [ -z "$NNN_PIPE" ]; then
|
||||
echo "No pipe file found" 1>&2
|
||||
|
@ -20,15 +27,35 @@ nnn_cd () {
|
|||
|
||||
if [ -n "$2" ]; then
|
||||
context=$2
|
||||
else
|
||||
elif [ $CUR_CTX -ne 1 ]; then
|
||||
printf "Choose context 1-4 (blank for current): "
|
||||
read -r context
|
||||
fi
|
||||
|
||||
printf "%s" "${context:-0}$dir" > "$NNN_PIPE"
|
||||
printf "%s" "${context:-0}c$dir" > "$NNN_PIPE"
|
||||
}
|
||||
|
||||
cmd_exists () {
|
||||
which "$1" > /dev/null 2>&1
|
||||
echo $?
|
||||
type "$1" > /dev/null 2>&1
|
||||
echo $?
|
||||
}
|
||||
|
||||
nnn_use_selection() {
|
||||
if ! [ -s "$selection" ]; then
|
||||
return 1
|
||||
fi
|
||||
|
||||
if [ "$NNN_PREFER_SELECTION" -eq 1 ]; then
|
||||
return 0
|
||||
else
|
||||
[ -n "$1" ] && printf "%s " "$1"
|
||||
printf "(s)election/(c)urrent? [default=c] "
|
||||
read -r resp__
|
||||
|
||||
if [ "$resp__" = "s" ]; then
|
||||
return 0
|
||||
else
|
||||
return 1
|
||||
fi
|
||||
fi
|
||||
}
|
||||
|
|
|
@ -4,17 +4,19 @@
|
|||
#
|
||||
# Details: nnn invokes this plugin to show notification when a cp/mv/rm operation is complete.
|
||||
#
|
||||
# Requires: notify-send (Ubuntu)/ntfy (https://github.com/dschep/ntfy)/osascript (macOS)
|
||||
# Dependencies: notify-send (Ubuntu)/ntfy (https://github.com/dschep/ntfy)/osascript (macOS)/notify (Haiku)
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Anna Arad
|
||||
|
||||
OS="$(uname)"
|
||||
|
||||
if which notify-send >/dev/null 2>&1; then
|
||||
if type notify-send >/dev/null 2>&1; then
|
||||
notify-send nnn "Done!"
|
||||
elif [ "$OS" = "Darwin" ]; then
|
||||
osascript -e 'display notification "Done!" with title "nnn"'
|
||||
elif which ntfy >/dev/null 2>&1; then
|
||||
elif type ntfy >/dev/null 2>&1; then
|
||||
ntfy -t nnn send "Done!"
|
||||
elif [ "$OS" = "Haiku" ]; then
|
||||
notify --title "nnn" "Done!"
|
||||
fi
|
||||
|
|
|
@ -3,130 +3,219 @@
|
|||
<p align="center"><img src="https://i.imgur.com/SpT0L2W.png" /></p>
|
||||
<p align="center"><i>read ebooks with plugin gutenread (Android)</i></p>
|
||||
|
||||
<p align="center"><img src="https://i.imgur.com/14iPDIq.png" /></p>
|
||||
<p align="center"><i>image preview with plugin imgthumb</i></p>
|
||||
|
||||
## Introduction
|
||||
|
||||
Plugins extend the capabilities of `nnn`. They are _executable_ scripts (or binaries) which `nnn` can communicate with and trigger. This mechanism fits perfectly with the fundamental design to keep the core file manager lean and fast, by delegating repetitive (but not necessarily file manager-specific) tasks to the plugins.
|
||||
Plugins extend the capabilities of `nnn`. They are _executable_ scripts (or binaries) `nnn` can communicate with and trigger. This mechanism fits perfectly with the fundamental design to keep the core file manager lean and fast, by delegating repetitive (but not necessarily file manager-specific) tasks to the plugins which can be run with custom hotkeys.
|
||||
|
||||
## Installing plugins
|
||||
|
||||
The following command installs or updates (after backup) all plugins:
|
||||
|
||||
curl -Ls https://raw.githubusercontent.com/jarun/nnn/master/plugins/getplugs | sh
|
||||
|
||||
Plugins are installed to `${XDG_CONFIG_HOME:-$HOME/.config}/nnn/plugins`.
|
||||
`nnn` is _**language-agnostic**_ when it comes to plugins. You can write a plugin in any (scripting) language you are comfortable in!
|
||||
|
||||
## List of plugins
|
||||
|
||||
| Plugin (a-z) | Description | Lang | Deps |
|
||||
| Plugin (a-z) | Description [Clears selection<sup>1</sup>] | Lang | Dependencies |
|
||||
| --- | --- | --- | --- |
|
||||
| autojump | Navigate to dir/path (**autojump stores navigation patterns**) | sh | autojump |
|
||||
| boom | Play random music from dir | sh | [moc](http://moc.daper.net/) |
|
||||
| dups | List non-empty duplicate files in current dir | sh | find, md5sum,<br>sort uniq xargs |
|
||||
| chksum | Create and verify checksums | sh | md5sum,<br>sha256sum |
|
||||
| diffs | Diff for selection (limited to 2 for directories) | sh | vimdiff |
|
||||
| dragdrop | Drag/drop files from/into nnn | sh | [dragon](https://github.com/mwh/dragon) |
|
||||
| fzcd | Change to the directory of a fuzzy-selected file/dir | sh | fzf/fzy<br>fd/fdfind/find |
|
||||
| fzhist | Fuzzy-select a cmd from history, edit in `$EDITOR` and run | sh | fzf/fzy |
|
||||
| fzopen | Fuzzy find a file in dir subtree and edit or open | sh | fzf/fzy, xdg-open |
|
||||
| getplugs | Update plugins | sh | curl |
|
||||
| gutenread | Browse, download, read from Project Gutenberg | sh | curl, unzip, w3m<br>[epr](https://github.com/wustho/epr) (optional) |
|
||||
| hexview | View a file in hex in `$PAGER` | sh | xxd |
|
||||
| imgresize | Resize images in dir to screen resolution | sh | [imgp](https://github.com/jarun/imgp) |
|
||||
| imgthumb | View thumbnail of an image or dir of images | sh | [lsix](https://github.com/hackerb9/lsix) |
|
||||
| imgur | Upload an image to imgur (from [imgur-screenshot](https://github.com/jomo/imgur-screenshot)) | bash | - |
|
||||
| imgview | Browse images, set wallpaper, copy path ([config](https://wiki.archlinux.org/index.php/Sxiv#Assigning_keyboard_shortcuts)), [rename](https://github.com/jarun/nnn/wiki/Basic-use-cases#browse-rename-images)| sh | sxiv/[viu](https://github.com/atanunq/viu), less|
|
||||
| ipinfo | Fetch external IP address and whois information | sh | curl, whois |
|
||||
| kdeconnect | Send selected files to an Android device | sh | kdeconnect-cli |
|
||||
| launch | GUI application launcher | sh | fzf/fzy |
|
||||
| mediainf | Show media information | sh | mediainfo |
|
||||
| moclyrics | Show lyrics of the track playing in moc | sh | [ddgr](https://github.com/jarun/ddgr), [moc](http://moc.daper.net/) |
|
||||
| mocplay | Append (and/or play) selection/dir/file in moc | sh | [moc](http://moc.daper.net/) |
|
||||
| nmount | Toggle mount status of a device as normal user | sh | pmount, udisks2 |
|
||||
| nuke | Sample file opener (CLI-only by default) | sh | various |
|
||||
| oldbigfile | List large files by access time | sh | find, sort |
|
||||
| organize | Auto-organize files in directories by file type | sh | file |
|
||||
| pdfread | Read a PDF or text file aloud | sh | pdftotext, mpv,<br>pico2wave |
|
||||
| pdfview | View PDF file in `$PAGER` | sh | pdftotext/<br>mupdf-tools |
|
||||
| picker | Pick files and list one per line (to pipe) | sh | nnn |
|
||||
| pskill | Fuzzy list by name and kill process or zombie | sh | fzf/fzy, ps,<br>sudo/doas |
|
||||
| renamer | Batch rename selection or files in dir | sh | [qmv](https://www.nongnu.org/renameutils/)/[vidir](https://joeyh.name/code/moreutils/) |
|
||||
| ringtone | Create a variable bitrate mp3 ringtone from file | sh | date, ffmpeg |
|
||||
| splitjoin | Split file or join selection | sh | split, cat |
|
||||
| suedit | Edit file using superuser permissions | sh | sudoedit/sudo/doas |
|
||||
| treeview | Informative tree output in `$EDITOR` | sh | tree |
|
||||
| uidgid | List user and group of all files in dir | sh | ls, less |
|
||||
| upgrade | Upgrade nnn manually on Debian 9 Stretch | sh | curl |
|
||||
| upload | Paste text to ix.io, upload binary to file.io | sh | curl, jq, tr |
|
||||
| vidthumb | Show video thumbnails in terminal | sh | [ffmpegthumbnailer](https://github.com/dirkvdb/ffmpegthumbnailer),<br>[lsix](https://github.com/hackerb9/lsix) |
|
||||
| wall | Set wallpaper or change colorscheme | sh | nitrogen/pywal |
|
||||
|
||||
## Invoking a plugin
|
||||
|
||||
Use the plugin shortcut (<kbd>;key</kbd> or <kbd>^Skey</kbd>) to list the defined plugin keys and press the required key. E.g., with the below config:
|
||||
|
||||
export NNN_PLUG='o:fzopen;p:mocplay;d:diffs;m:nmount;n:notes;v:imgviu;t:imgthumb'
|
||||
|
||||
Plugin `fzopen` can be run with the keybind <kbd>;o</kbd>, `mocplay` can be run with <kbd>;p</kbd> and so on... The key vs. plugin pairs are shown in the help and config screen.
|
||||
|
||||
A maximum of 15 keys can be defined. To select and invoke a plugin from the plugin directory, press <kbd>Enter</kbd> (to _enter_ the plugin dir) after the plugin shortcut.
|
||||
|
||||
#### Skip directory refresh after running a plugin
|
||||
|
||||
`nnn` refreshes the directory after running a plugin to reflect any changes by the plugin. To disable this (say while running the `mediainfo` plugin on some filtered files), add a `-` before the plugin name:
|
||||
|
||||
export NNN_PLUG='m:-mediainfo'
|
||||
|
||||
Now `nnn` will not refresh the directory after running the `mediainfo` plugin.
|
||||
|
||||
## Running commands as plugin
|
||||
|
||||
To assign keys to arbitrary non-background, non-shell-interpreted cli commands and invoke like plugins, add `_` (underscore) before the command.
|
||||
|
||||
For example:
|
||||
|
||||
export NNN_PLUG='x:_chmod +x $nnn;g:_git log;s:_smplayer $nnn;o:fzopen'
|
||||
|
||||
Now <kbd>;x</kbd> can be used to make a file executable, <kbd>;g</kbd> can be used to the git log of a git project directory, <kbd>;s</kbd> can be used to preview a partially downloaded media file.
|
||||
|
||||
#### Skip user confirmation after command execution
|
||||
|
||||
`nnn` waits for user confirmation (the prompt `Press Enter to continue`) after it executes a command as plugin (unlike plugins which can add a `read` to wait). To skip this, add a `*` after the command. For example:
|
||||
|
||||
export NNN_PLUG='s:_smplayer $nnn*;n:-_vim /home/vaio/Dropbox/Public/synced_note*'
|
||||
|
||||
Now there will be no prompt after <kbd>;s</kbd> and <kbd>;n</kbd>.
|
||||
| [autojump](autojump) | Navigate to dir/path | sh | [jump](https://github.com/gsamokovarov/jump)/autojump/<br>zoxide/z/[z.lua](https://github.com/skywind3000/z.lua) |
|
||||
| [boom](boom) | Play random music from dir | sh | [moc](http://moc.daper.net/) |
|
||||
| [bulknew](bulknew) | Create multiple files/dirs at once | bash | sed, xargs, mktemp |
|
||||
| [cbcopy-mac](cbcopy-mac) | Copy the hovered file to MacOS clipboard | applescript | macos |
|
||||
| [cbpaste-mac](cbpaste-mac) | Pastes files from MacOS clipboard into currect directory | macos |
|
||||
| [cdpath](cdpath) | `cd` to the directory from `CDPATH` | sh | fzf |
|
||||
| [chksum](chksum) | Create and verify checksums [✓] | sh | md5sum,<br>sha256sum |
|
||||
| [cmusq](cmusq) | Queue/play files/dirs in cmus player [✓] | sh | cmus, pgrep |
|
||||
| [diffs](diffs) | Diff for selection (limited to 2 for directories) [✓] | sh | vimdiff, mktemp |
|
||||
| [dragdrop](dragdrop) | Drag/drop files from/into nnn | sh | [dragon](https://github.com/mwh/dragon) |
|
||||
| [dups](dups) | List non-empty duplicate files in current dir | bash | find, md5sum,<br>sort uniq xargs |
|
||||
| [finder](finder) | Run custom find command (**stored in histfile**) and list | sh | - |
|
||||
| [fixname](fixname) | Clean filename to be more shell-friendly [✓] | bash | sed |
|
||||
| [fzcd](fzcd) | Fuzzy search multiple dirs (or `$PWD`) and visit file | sh | fzf, (find) |
|
||||
| [fzhist](fzhist) | Fuzzy-select a cmd from history, edit in `$EDITOR` and run | sh | fzf, mktemp |
|
||||
| [fzopen](fzopen) | Fuzzy find file(s) in subtree to edit/open/pick | sh | fzf, xdg-open/open |
|
||||
| [fzplug](fzplug) | Fuzzy find, preview and run other plugins | sh | fzf |
|
||||
| [getplugs](getplugs) | Update plugins to installed `nnn` version | sh | curl |
|
||||
| [gitroot](gitroot) | Cd to the root of current git repo | sh | git |
|
||||
| [gpge](gpge) | Encrypt/decrypt files using GPG [✓] | sh | gpg |
|
||||
| [gutenread](gutenread) | Browse, download, read from Project Gutenberg | sh | curl, unzip, w3m<br>[epr](https://github.com/wustho/epr) (optional) |
|
||||
| [gsconnect](gsconnect) | GNOME's implementation of kdeconnect [✓] | sh | gsconnect |
|
||||
| [imgresize](imgresize) | Batch resize images in dir to screen resolution | sh | [imgp](https://github.com/jarun/imgp) |
|
||||
| [imgur](imgur) | Upload an image to imgur (from [imgur-screenshot](https://github.com/jomo/imgur-screenshot)) | bash | - |
|
||||
| [imgview](imgview) | View (thumbnail)images, set wallpaper, [rename](https://github.com/jarun/nnn/wiki/Basic-use-cases#browse-rename-images) and [more](https://wiki.archlinux.org/index.php/Sxiv#Assigning_keyboard_shortcuts)| sh | _see in-file docs_ |
|
||||
| [ipinfo](ipinfo) | Fetch external IP address and whois information | sh | curl, whois |
|
||||
| [kdeconnect](kdeconnect) | Send selected files to an Android device [✓] | sh | kdeconnect-cli |
|
||||
| [launch](launch) | GUI application launcher | sh | fzf |
|
||||
| [mimelist](mimelist) | List files by mime in subtree | sh | file/mimetype |
|
||||
| [moclyrics](moclyrics) | Show lyrics of the track playing in moc | sh | [ddgr](https://github.com/jarun/ddgr), [moc](http://moc.daper.net/) |
|
||||
| [mocq](mocq) | Queue/play selection/dir/file in moc [✓] | sh | [moc](http://moc.daper.net/) |
|
||||
| [mp3conv](mp3conv) | Extract audio from multimedia as mp3 | sh | ffmpeg |
|
||||
| [mtpmount](mtpmount) | Toggle mount of MTP device (eg. Android) | sh | gvfs-mtp |
|
||||
| [nbak](nbak) | Backs up `nnn` config | sh | tar, awk, mktemp |
|
||||
| [nmount](nmount) | Toggle mount status of a device as normal user | sh | pmount (optional), udisks2 |
|
||||
| [nuke](nuke) | Sample file opener (CLI-only by default) | sh | _see in-file docs_ |
|
||||
| [oldbigfile](oldbigfile) | List large files by access time | sh | find, sort |
|
||||
| [openall](openall) | Open selected files together or one by one [✓] | bash | - |
|
||||
| [organize](organize) | Auto-organize files in directories by file type [✓] | sh | file |
|
||||
| [pdfread](pdfread) | Read a PDF or text file aloud | sh | pdftotext, mpv,<br>pico2wave |
|
||||
| [preview-tabbed](preview-tabbed) | Preview files with Tabbed/xembed | bash | _see in-file docs_ |
|
||||
| [preview-tui](preview-tui) | Preview with Tmux/kitty/[QuickLook](https://github.com/QL-Win/QuickLook)/xterm/`$TERMINAL` | sh | _see in-file docs_ |
|
||||
| [pskill](pskill) | Fuzzy list by name and kill process or zombie | sh | fzf, ps, sudo/doas |
|
||||
| [renamer](renamer) | Batch rename selection or files in dir [✓] | sh | [qmv](https://www.nongnu.org/renameutils/)/[vidir](https://joeyh.name/code/moreutils/) |
|
||||
| [ringtone](ringtone) | Create a variable bitrate mp3 ringtone from file | sh | date, ffmpeg |
|
||||
| [rsynccp](rsynccp) | Gives copy-paste verbose progress percentage [✓] | sh | rsync |
|
||||
| [splitjoin](splitjoin) | Split file or join selection [✓] | sh | split, cat |
|
||||
| [suedit](suedit) | Edit file using superuser permissions | sh | sudoedit/sudo/doas |
|
||||
| [togglex](togglex) | Toggle executable mode for selection [✓] | sh | chmod |
|
||||
| [umounttree](umounttree) | Unmount a remote mountpoint from within | sh | fusermount |
|
||||
| [upload](upload) | Upload to Firefox Send or ix.io (text) or file.io (bin) | sh | [ffsend](https://github.com/timvisee/ffsend), curl, jq, tr |
|
||||
| [wallpaper](wallpaper) | Set wallpaper or change colorscheme | sh | nitrogen/pywal |
|
||||
| [x2sel](x2sel) | Copy file list from system clipboard to selection | sh | _see in-file docs_ |
|
||||
| [xdgdefault](xdgdefault) | Set the default app for the hovered file type | sh | xdg-utils, fzf/dmenu |
|
||||
|
||||
Notes:
|
||||
|
||||
1. Use single quotes for `$NNN_PLUG` so `$nnn` is not interpreted
|
||||
2. `$nnn` should be the last argument (IF used)
|
||||
3. (_Again_) add `_` before the command
|
||||
4. To disable directory refresh after running a _command as plugin_, prefix with `-_`
|
||||
1. A plugin has to explicitly request `nnn` to clear the selection e.g. after operating on the selected files.
|
||||
2. Files starting with a dot in the `plugins` directory are internal files and should not be used as plugins.
|
||||
|
||||
### Table of contents
|
||||
|
||||
- [Installation](#installation)
|
||||
- [Configuration](#configuration)
|
||||
- [Skip directory refresh after running a plugin](#skip-directory-refresh-after-running-a-plugin--)
|
||||
- [Running commands as plugin](#running-commands-as-plugin-)
|
||||
- [Skip user confirmation after command execution](#skip-user-confirmation-after-command-execution-)
|
||||
- [Run a GUI app as plugin](#run-a-gui-app-as-plugin-)
|
||||
- [Page non-interactive command output](#page-non-interactive-command-output-)
|
||||
- [Some useful key-command examples](#some-useful-key-command-examples)
|
||||
- [Access level of plugins](#access-level-of-plugins)
|
||||
- [Create your own plugins](#create-your-own-plugins)
|
||||
- [Send data to `nnn`](#send-data-to-nnn)
|
||||
- [Get notified on file hover](#get-notified-on-file-hover)
|
||||
- [Examples](#examples)
|
||||
- [Contributing plugins](#contributing-plugins)
|
||||
|
||||
## Installation
|
||||
|
||||
The following command installs or updates (after backup) all plugins:
|
||||
|
||||
```sh
|
||||
sh -c "$(curl -Ls https://raw.githubusercontent.com/jarun/nnn/master/plugins/getplugs)"
|
||||
```
|
||||
|
||||
Plugins are installed to `${XDG_CONFIG_HOME:-$HOME/.config}/nnn/plugins`.
|
||||
|
||||
## Configuration
|
||||
|
||||
Set environment variable `NNN_PLUG` to assign keybinds and invoke plugins directly using the plugin shortcut (<kbd>;</kbd>) followed by the assigned key character. E.g., with the below config:
|
||||
|
||||
```sh
|
||||
export NNN_PLUG='f:finder;o:fzopen;p:mocq;d:diffs;t:nmount;v:imgview'
|
||||
```
|
||||
|
||||
plugin `finder` can be invoked with the keybind <kbd>;f</kbd>, `fzopen` can be run with <kbd>;o</kbd> and so on... The key vs. plugin pairs are shown in the help and config screen.
|
||||
|
||||
Alternatively, combine with <kbd>Alt</kbd> (i.e. <kbd>Alt+key</kbd>).
|
||||
|
||||
To pick and run an unassigned plugin, press <kbd>Enter</kbd> (to _enter_ the plugin dir) at the plugin prompt.
|
||||
|
||||
To run a plugin at startup, use the option `-P` followed by the plugin key.
|
||||
|
||||
If the plugins list gets too long, try breaking them up into sections:
|
||||
|
||||
```
|
||||
NNN_PLUG_PERSONAL='g:personal/convert2zoom;p:personal/echo'
|
||||
NNN_PLUG_WORK='j:work/prettyjson;d:work/foobar'
|
||||
NNN_PLUG_INLINE='e:!go run "$nnn"*'
|
||||
NNN_PLUG_DEFAULT='1:ipinfo;p:preview-tui;o:fzz;b:nbak'
|
||||
NNN_PLUG="$NNN_PLUG_PERSONAL;$NNN_PLUG_WORK;$NNN_PLUG_DEFAULT;$NNN_PLUG_INLINE"
|
||||
export NNN_PLUG
|
||||
```
|
||||
|
||||
Note:
|
||||
- `'g:personal/convert2zoom'` will look in the personal sub-folder inside the plugin folder.
|
||||
- `'b:boom;b:bulknew` will result in only the first definition of *b* (`b:boom`) being used.
|
||||
- A keybinding definition of more than 1 character will prevent nnn from starting.
|
||||
|
||||
|
||||
#### Skip directory refresh after running a plugin [`-`]
|
||||
|
||||
`nnn` refreshes the directory after running a plugin to reflect any changes by the plugin. To disable this add a `-` before the plugin name:
|
||||
|
||||
```sh
|
||||
export NNN_PLUG='p:-plugin'
|
||||
```
|
||||
|
||||
## Running commands as plugin [`!`]
|
||||
|
||||
To assign keys to arbitrary non-background cli commands and invoke like plugins, add `!` before the command.
|
||||
|
||||
```sh
|
||||
export NNN_PLUG='x:!chmod +x "$nnn";g:!git log;s:!smplayer "$nnn"'
|
||||
```
|
||||
|
||||
Now <kbd>;x</kbd> can be used to make a file executable, <kbd>;g</kbd> can be used to the git log of a git project directory, <kbd>;s</kbd> can be used to preview a partially downloaded media file.
|
||||
|
||||
#### Skip user confirmation after command execution [`*`]
|
||||
|
||||
`nnn` waits for user confirmation (the prompt `Press Enter to continue`) after it executes a command as plugin (unlike plugins which can add a `read` to wait). To skip this, add a `*` after the command.
|
||||
|
||||
```sh
|
||||
export NNN_PLUG='s:!smplayer "$nnn"*;n:-!vim /home/vaio/Dropbox/Public/synced_note*'
|
||||
```
|
||||
|
||||
Now there will be no prompt after <kbd>;s</kbd> and <kbd>;n</kbd>.
|
||||
|
||||
Note: Do not use `*` with programs that run and exit e.g. cat.
|
||||
|
||||
#### Run a GUI app as plugin [`&`]
|
||||
|
||||
To run a GUI app as plugin, add a `&` after `!`.
|
||||
|
||||
```sh
|
||||
export NNN_PLUG='m:-!&mousepad "$nnn"'
|
||||
```
|
||||
|
||||
#### Page non-interactive command output [`|`]
|
||||
|
||||
To show the output of run-and-exit commands which do not need user input, add `|` (pipe) after `!`.
|
||||
|
||||
```sh
|
||||
export NNN_PLUG='m:-!|mediainfo "$nnn";t:-!|tree -ps;l:-!|ls -lah --group-directories-first'
|
||||
```
|
||||
|
||||
This option is incompatible with `&` (terminal output is masked for GUI programs) and ignores `*` (output is already paged for user).
|
||||
|
||||
Notes:
|
||||
1. Place `$nnn` (or exported variables) in double quotes (**`"$nnn"`**)
|
||||
2. Use single quotes for `$NNN_PLUG` so `"$nnn"` is not interpreted
|
||||
3. (_Again_) add `!` before the command
|
||||
4. To disable directory refresh after running a _command as plugin_, prefix with `-!`
|
||||
|
||||
#### Some useful key-command examples
|
||||
|
||||
| Key:Command | Description |
|
||||
|---|---|
|
||||
| `e:-_vi $nnn*` | Edit hovered file in vi |
|
||||
| `k:-_fuser -kiv $nnn*` | Interactively kill process(es) using hovered file |
|
||||
| `l:_git log` | Show git log |
|
||||
| `n:-_vi /home/user/Dropbox/dir/note*` | Take quick notes in a synced file/dir of notes |
|
||||
| `p:-_less -iR $nnn*` | Page through hovered file in less |
|
||||
| `s:_smplayer -minigui $nnn*` | Play hovered media file, even unfinished download |
|
||||
| `x:_chmod +x $nnn` | Make the hovered file executable |
|
||||
| `y:-_sync*` | Flush cached writes |
|
||||
| `c:!convert "$nnn" png:- \| xclip -sel clipboard -t image/png*` | Copy image to clipboard |
|
||||
| `C:!cp -rv "$nnn" "$nnn".cp` | Create a copy of the hovered file |
|
||||
| `e:-!sudo -E vim "$nnn"*` | Edit file as root in vim |
|
||||
| `g:-!git diff` | Show git diff |
|
||||
| `h:-!hx "$nnn"*` | Open hovered file in [hx](https://github.com/krpors/hx) hex editor |
|
||||
| `k:-!fuser -kiv "$nnn"*` | Interactively kill process(es) using hovered file |
|
||||
| `l:-!git log` | Show git log |
|
||||
| `n:-!vi /home/user/Dropbox/dir/note*` | Take quick notes in a synced file/dir of notes |
|
||||
| `p:-!less -iR "$nnn"*` | Page through hovered file in less |
|
||||
| `s:-!&smplayer -minigui "$nnn"` | Play hovered media file, even unfinished download |
|
||||
| `x:!chmod +x "$nnn"` | Make the hovered file executable |
|
||||
| `y:-!sync*` | Flush cached writes |
|
||||
|
||||
## Access level of plugins
|
||||
|
||||
When `nnn` executes a plugin, it does the following:
|
||||
- Changes to the directory where the plugin is to be run (`$PWD` pointing to the active directory)
|
||||
- Passes two arguments to the script:
|
||||
1. The hovered file's name.
|
||||
2. The working directory (might differ from `$PWD` in case of symlinked paths; non-canonical).
|
||||
- Passes three arguments to the script:
|
||||
1. `$1`: The hovered file's name.
|
||||
2. `$2`: The working directory (might differ from `$PWD` in case of symlinked paths; non-canonical).
|
||||
3. `$3`: The picker mode output file (`-` for stdout) if `nnn` is executed as a file picker.
|
||||
- Sets the environment variable `NNN_PIPE` used to control `nnn` active directory.
|
||||
- Sets the environment variable `NNN_INCLUDE_HIDDEN` to `1` if hidden files are active, `0` otherwise.
|
||||
- Sets the environment variable `NNN_PREFER_SELECTION` to `1` if user prefers to use selection (see nnn's `-u` flag), `0` otherwise.
|
||||
- Exports the [special variables](https://github.com/jarun/nnn/wiki/Concepts#special-variables).
|
||||
|
||||
Plugins can also read the `.selection` file in the config directory.
|
||||
|
||||
|
@ -134,55 +223,161 @@ Plugins can also read the `.selection` file in the config directory.
|
|||
|
||||
Plugins can be written in any scripting language. However, POSIX-compliant shell scripts runnable in `sh` are preferred.
|
||||
|
||||
Drop the plugin in `${XDG_CONFIG_HOME:-$HOME/.config}/nnn/plugins` and make it executable. Optionally add a hotkey in `$NNN_PLUG` for frequent usage.
|
||||
**Make the file executable**. Drop it in the plugin directory. Optionally add a hotkey in `$NNN_PLUG` for frequent usage.
|
||||
|
||||
#### Controlling `nnn`'s active directory
|
||||
`nnn` provides a mechanism for plugins to control its active directory.
|
||||
#### Send data to `nnn`
|
||||
`nnn` provides a mechanism for plugins to send data to `nnn` to control its active directory or invoke the list mode.
|
||||
The way to do so is by writing to the pipe pointed by the environment variable `NNN_PIPE`.
|
||||
The plugin should write a single string in the format `<number><path>` without a newline at the end. For example, `1/etc`.
|
||||
The number indicates the context to change the active directory of (0 is used to indicate the current context).
|
||||
The plugin should write a single string in the format `(<->)<ctxcode><opcode><data>` without a newline at the end. For example, `1c/etc`.
|
||||
|
||||
The optional `-` at the **beginning of the stream** instructs `nnn` to clear the selection.
|
||||
In cases where the data transfer to `nnn` has to happen while the selection file is being read (e.g. in a loop), the plugin should
|
||||
create a tmp copy of the selection file, inform `nnn` to clear the selection and then do the subsequent processing with the tmp file.
|
||||
A paged [`|`] or GUI [`&`] cmd run as plugin cannot clear selection.
|
||||
|
||||
The `ctxcode` indicates the context to change the active directory of.
|
||||
|
||||
| Context code | Meaning |
|
||||
|:---:| --- |
|
||||
| `+` | smart context (next inactive else current) |
|
||||
| `0` | current context |
|
||||
| `1`-`4` | context number |
|
||||
|
||||
The `opcode` indicates the operation type.
|
||||
|
||||
| Opcode | Operation |
|
||||
|:---:| --- |
|
||||
| `c` | change directory |
|
||||
| `l` | list files in list mode |
|
||||
| `p` | picker file overwritten |
|
||||
|
||||
For convenience, we provided a helper script named `.nnn-plugin-helper` and a function named `nnn_cd` to ease this process. `nnn_cd` receives the path to change to as the first argument, and the context as an optional second argument.
|
||||
If a context is not provided, it is asked for explicitly.
|
||||
If a context is not provided, it is asked for explicitly. To skip this and choose the current context, set the `CUR_CTX` variable in `.nnn-plugin-helper` (or in the specific plugin after sourcing `.nnn-plugin-helper`) to 1.
|
||||
Usage examples can be found in the Examples section below.
|
||||
|
||||
#### Examples
|
||||
#### Get notified on file hover
|
||||
|
||||
If `NNN_FIFO` is set, `nnn` will open it and write every hovered files. This can be used in plugins and external scripts, e.g. to implement file previews.
|
||||
|
||||
Don't forget to fork in the background to avoid blocking `nnn`.
|
||||
|
||||
For more details on configuration and usage of the preview plugins, visit [Live Previews](https://github.com/jarun/nnn/wiki/Live-previews).
|
||||
|
||||
## Examples
|
||||
|
||||
There are many plugins provided by `nnn` which can be used as examples. Here are a few simple selected examples.
|
||||
|
||||
- Show the git log of changes to the particular file along with the code for a quick and easy review.
|
||||
```sh
|
||||
#!/usr/bin/env sh
|
||||
git log -p -- "$1"
|
||||
```
|
||||
#### Show the git log of changes to the particular file along with the code for a quick and easy review.
|
||||
|
||||
- Change to directory in clipboard using helper script
|
||||
```sh
|
||||
#!/usr/bin/env sh
|
||||
. $(dirname $0)/.nnn-plugin-helper
|
||||
```sh
|
||||
#!/usr/bin/env sh
|
||||
|
||||
nnn_cd "$(xsel -ob)"
|
||||
```
|
||||
git log -p -- "$1"
|
||||
```
|
||||
|
||||
- Change directory to the location of a link using helper script with specific context (current)
|
||||
```sh
|
||||
#!/usr/bin/env sh
|
||||
. $(dirname $0)/.nnn-plugin-helper
|
||||
#### Change to directory in clipboard using helper script
|
||||
|
||||
nnn_cd "$(dirname $(readlink -fn $1))" 0
|
||||
```
|
||||
```sh
|
||||
#!/usr/bin/env sh
|
||||
|
||||
- Change to arbitrary directory without helper script
|
||||
```sh
|
||||
#!/usr/bin/env sh
|
||||
printf "cd to: "
|
||||
read -r dir
|
||||
. $(dirname $0)/.nnn-plugin-helper
|
||||
|
||||
printf "%s" "0$dir" > "$NNN_PIPE"
|
||||
```
|
||||
nnn_cd "$(xsel -ob)"
|
||||
```
|
||||
|
||||
#### Change directory to the location of a link using helper script with specific context (current)
|
||||
|
||||
```sh
|
||||
#!/usr/bin/env sh
|
||||
|
||||
. $(dirname $0)/.nnn-plugin-helper
|
||||
|
||||
nnn_cd "$(dirname $(readlink -fn $1))" 0
|
||||
```
|
||||
|
||||
#### Change to arbitrary directory without helper script
|
||||
|
||||
```sh
|
||||
#!/usr/bin/env sh
|
||||
|
||||
printf "cd to: "
|
||||
read -r dir
|
||||
|
||||
printf "%s" "0c$dir" > "$NNN_PIPE"
|
||||
```
|
||||
|
||||
#### Send every hovered file to X selection
|
||||
|
||||
```sh
|
||||
#!/usr/bin/env sh
|
||||
|
||||
if [ -z "$NNN_FIFO" ] ; then
|
||||
exit 1
|
||||
fi
|
||||
|
||||
while read FILE ; do
|
||||
printf "%s" "$FILE" | xsel
|
||||
done < "$NNN_FIFO" &
|
||||
disown
|
||||
```
|
||||
|
||||
#### Quick `find` the first match in subtree and open in `nuke`
|
||||
|
||||
```sh
|
||||
#!/usr/bin/env sh
|
||||
|
||||
NUKE="${XDG_CONFIG_HOME:-$HOME/.config}/nnn/plugins/nuke"
|
||||
|
||||
printf "file name: "
|
||||
read -r pattern
|
||||
|
||||
entry=$(find . -type f -iname "$pattern" -print -quit 2>/dev/null)
|
||||
|
||||
if [ -n "$entry" ]; then
|
||||
"$NUKE" "$entry"
|
||||
fi
|
||||
```
|
||||
|
||||
#### Quick find (using `fd`)
|
||||
|
||||
```sh
|
||||
#!/usr/bin/env sh
|
||||
|
||||
. "$(dirname "$0")"/.nnn-plugin-helper
|
||||
|
||||
printf "pattern: "
|
||||
read -r pattern
|
||||
|
||||
if [ -n "$pattern" ]; then
|
||||
printf "%s" "+l" > "$NNN_PIPE"
|
||||
eval "fd -HI $pattern -0" > "$NNN_PIPE"
|
||||
fi
|
||||
```
|
||||
|
||||
#### Quick grep (using `rg`)
|
||||
|
||||
```sh
|
||||
#!/usr/bin/env sh
|
||||
|
||||
. "$(dirname "$0")"/.nnn-plugin-helper
|
||||
|
||||
printf "pattern: "
|
||||
read -r pattern
|
||||
|
||||
if [ -n "$pattern" ]; then
|
||||
printf "%s" "+l" > "$NNN_PIPE"
|
||||
eval "rg -l0 --hidden -S $pattern" > "$NNN_PIPE"
|
||||
fi
|
||||
```
|
||||
|
||||
#### Change directory
|
||||
|
||||
NNN_PLUG='c:!read -r to && [ -n "$to" ] && printf "0c%s" "${to}" > "$NNN_PIPE"*'
|
||||
|
||||
## Contributing plugins
|
||||
|
||||
1. Add informative sections like _Description_, _Notes_, _Dependencies_, _Shell_, _Author_ etc. in the plugin.
|
||||
2. Add an entry in the table above.
|
||||
2. Add an entry in the table above. Note that the list is alphabetically ordered by plugin name.
|
||||
3. Keep non-portable commands (like `notify-send`) commented so users from any other OS/DE aren't surprised.
|
||||
4. The plugin file should be executable.
|
||||
5. If your plugin stores data, use `${XDG_CACHE_HOME:-$HOME/.cache}/nnn`. Document it _in-file_.
|
||||
|
|
|
@ -1,20 +1,74 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: Navigate to directory using autojump
|
||||
# Description: Navigate to directory using jump/autojump/zoxide/z
|
||||
#
|
||||
# Requires: autojump - https://github.com/wting/autojump
|
||||
# Dependencies:
|
||||
# - jump - https://github.com/gsamokovarov/jump
|
||||
# - OR autojump - https://github.com/wting/autojump
|
||||
# - OR zoxide - https://github.com/ajeetdsouza/zoxide
|
||||
# - OR z - https://github.com/rupa/z (z requires fzf)
|
||||
# - OR z (fish) - https://github.com/jethrokuan/z (z requires fzf)
|
||||
# - OR z.lua - https://github.com/skywind3000/z.lua (z.lua can enhanced with fzf)
|
||||
#
|
||||
# Note: autojump STORES NAVIGATION PATTERNS
|
||||
# Note: The dependencies STORE NAVIGATION PATTERNS
|
||||
#
|
||||
# to make z.lua work, you need to set $NNN_ZLUA to the path of script z.lua
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Marty Buchaus
|
||||
# Authors: Marty Buchaus, Dave Snider, Tim Adler, Nick Waywood
|
||||
|
||||
if which autojump >/dev/null 2>&1; then
|
||||
printf "jump to: "
|
||||
if [ ! -p "$NNN_PIPE" ]; then
|
||||
printf 'ERROR: NNN_PIPE is not set!'
|
||||
read -r _
|
||||
exit 2
|
||||
fi
|
||||
|
||||
if type jump >/dev/null 2>&1; then
|
||||
printf "jump to : "
|
||||
IFS= read -r line
|
||||
# shellcheck disable=SC2086
|
||||
odir="$(jump cd ${line})"
|
||||
printf "%s" "0c$odir" > "$NNN_PIPE"
|
||||
elif type autojump >/dev/null 2>&1; then
|
||||
printf "jump to : "
|
||||
read -r dir
|
||||
odir="$(autojump "$dir")"
|
||||
printf "%s" "0$odir" > "$NNN_PIPE"
|
||||
printf "%s" "0c$odir" > "$NNN_PIPE"
|
||||
elif type zoxide >/dev/null 2>&1; then
|
||||
if type fzf >/dev/null 2>&1; then
|
||||
odir="$(zoxide query -i --)"
|
||||
printf "%s" "0c$odir" > "$NNN_PIPE"
|
||||
else
|
||||
printf "jump to : "
|
||||
read -r dir
|
||||
odir="$(zoxide query -- "$dir")"
|
||||
printf "%s" "0c$odir" > "$NNN_PIPE"
|
||||
fi
|
||||
elif type lua >/dev/null 2>&1 && [ -n "$NNN_ZLUA" ]; then
|
||||
printf "jump to : "
|
||||
read -r line
|
||||
if type fzf >/dev/null 2>&1; then
|
||||
odir="$(lua "$NNN_ZLUA" -l "$line" | fzf --nth 2.. --reverse --inline-info --tac +s -e --height 35%)"
|
||||
printf "%s" "0c$(echo "$odir" | awk '{print $2}')" > "$NNN_PIPE"
|
||||
else
|
||||
odir="$(lua "$NNN_ZLUA" -e "$line")"
|
||||
printf "%s" "0c$odir" > "$NNN_PIPE"
|
||||
fi
|
||||
else
|
||||
printf "autojump missing"
|
||||
read -r _
|
||||
# rupa/z uses $_Z_DATA, jethrokuan/z (=port of z for fish) uses $Z_DATA
|
||||
datafile="${_Z_DATA:-${Z_DATA:-$HOME/.z}}"
|
||||
if type fzf >/dev/null 2>&1 && [ -f "$datafile" ]; then
|
||||
# Read the data from z's file instead of calling
|
||||
# z so the data doesn't need to be processed twice
|
||||
sel=$(awk -F "|" '{print $1}' "$datafile" | fzf | awk '{$1=$1};1')
|
||||
|
||||
# NOTE: Uncomment this line and comment out the line above if
|
||||
# you want to see the weightings of the dir's in the fzf pane
|
||||
# sel=$(awk -F "|" '{printf "%s %s\n", $2, $1}' "$datafile" | fzf | sed 's/^[0-9,.]* *//' | awk '{$1=$1};1')
|
||||
|
||||
printf "%s" "0c$sel" > "$NNN_PIPE"
|
||||
else
|
||||
printf "No supported autojump script [jump/autojump/zoxide/z (needs fzf)] found"
|
||||
read -r _
|
||||
fi
|
||||
fi
|
||||
|
|
40
plugins/boom
40
plugins/boom
|
@ -1,30 +1,46 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: Play random music from current directory. Identifies MP3, FLAC, M4A, WEBM, WMA.
|
||||
# You may want to set GUIPLAYER.
|
||||
# Description: Play random music (MP3, FLAC, M4A, WEBM, WMA) from current dir.
|
||||
#
|
||||
# Dependencies: mocp (or custom)
|
||||
#
|
||||
# Note: You may want to set GUIPLAYER.
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Arun Prakash Jana
|
||||
|
||||
#GUIPLAYER=smplayer
|
||||
GUIPLAYER="${GUIPLAYER:-""}"
|
||||
NUMTRACKS="${NUMTRACKS:-100}"
|
||||
|
||||
NUMTRACKS=100
|
||||
|
||||
if [ ! -z "$GUIPLAYER" ]; then
|
||||
PLAYER="$GUIPLAYER"
|
||||
find . -type f \( -iname "*.mp3" -o -iname "*.flac" -o -iname "*.m4a" -o -iname "*.webm" -o -iname "*.wma" \) | shuf | head -n $NUMTRACKS | xargs -d "\n" "$PLAYER" > /dev/null 2>&1 &
|
||||
if [ -n "$GUIPLAYER" ]; then
|
||||
find . -type f \( -iname "*.mp3" -o -iname "*.flac" -o -iname "*.m4a" -o -iname "*.webm" -o -iname "*.wma" \) | shuf -n "$NUMTRACKS" | xargs -d "\n" "$GUIPLAYER" > /dev/null 2>&1 &
|
||||
|
||||
# detach the player
|
||||
sleep 1
|
||||
elif which mocp >/dev/null 2>&1; then
|
||||
# start MOC server
|
||||
mocp -S
|
||||
elif type mocp >/dev/null 2>&1; then
|
||||
cmd=$(pgrep -x mocp 2>/dev/null)
|
||||
ret=$cmd
|
||||
|
||||
if [ -z "$ret" ]; then
|
||||
# start MOC server
|
||||
mocp -S
|
||||
mocp -o shuffle
|
||||
else
|
||||
# mocp running, check if it's playing
|
||||
state=$(mocp -i | grep "State:" | cut -d' ' -f2)
|
||||
if [ "$state" = 'PLAY' ]; then
|
||||
# add up to 100 random audio files
|
||||
find . -type f \( -iname "*.mp3" -o -iname "*.flac" -o -iname "*.m4a" -o -iname "*.webm" -o -iname "*.wma" \) | head -n "$NUMTRACKS" | xargs -d "\n" mocp -a
|
||||
exit
|
||||
fi
|
||||
fi
|
||||
|
||||
# clear MOC playlist
|
||||
mocp -c
|
||||
mocp -o shuffle
|
||||
|
||||
# add up to 100 random audio files
|
||||
find . -type f \( -iname "*.mp3" -o -iname "*.flac" -o -iname "*.m4a" -o -iname "*.webm" -o -iname "*.wma" \) | shuf | head -n $NUMTRACKS | xargs -d "\n" mocp -a
|
||||
find . -type f \( -iname "*.mp3" -o -iname "*.flac" -o -iname "*.m4a" -o -iname "*.webm" -o -iname "*.wma" \) | head -n "$NUMTRACKS" | xargs -d "\n" mocp -a
|
||||
|
||||
# start playing
|
||||
mocp -p
|
||||
|
|
|
@ -0,0 +1,32 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: Allows for creation of multiple files/dirs simultaneously
|
||||
# Creates a tmp file to write each entry in a separate line
|
||||
#
|
||||
# Note: Only relative paths are supported. Absolute paths are ignored
|
||||
# Leading and trailing whitespace in path names is also ignored
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: KlzXS
|
||||
|
||||
EDITOR="${EDITOR:-vi}"
|
||||
TMPDIR="${TMPDIR:-/tmp}"
|
||||
|
||||
printf "'f'ile / 'd'ir? "
|
||||
read -r resp
|
||||
|
||||
if [ "$resp" = "f" ]; then
|
||||
#shellcheck disable=SC2016
|
||||
cmd='mkdir -p "$(dirname "{}")" && touch "{}"'
|
||||
elif [ "$resp" = "d" ]; then
|
||||
cmd='mkdir -p {}'
|
||||
else
|
||||
exit 1
|
||||
fi
|
||||
|
||||
tmpfile=$(mktemp "$TMPDIR/.nnnXXXXXX")
|
||||
$EDITOR "$tmpfile"
|
||||
|
||||
sed "/^\//d" "$tmpfile" | xargs -n1 -I{} sh -c "$cmd"
|
||||
|
||||
rm -- "$tmpfile"
|
|
@ -0,0 +1,16 @@
|
|||
#!/usr/bin/osascript
|
||||
|
||||
# Description: Copy the hovered file to MacOS clipboard.
|
||||
#
|
||||
# Note: Supports only MacOS
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Syed Umar Anis
|
||||
|
||||
|
||||
on run args
|
||||
set filePath to (second item of args & "/" & first item of args)
|
||||
tell application "Finder"
|
||||
set the clipboard to (filePath as POSIX file)
|
||||
end tell
|
||||
end
|
|
@ -0,0 +1,24 @@
|
|||
#!/usr/bin/env sh
|
||||
# shellcheck disable=all
|
||||
|
||||
# Description: Paste the clipboard files into the current directory.
|
||||
# Only works if clipboard contents are files.
|
||||
#
|
||||
# Note: Supports only MacOS
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Syed Umar Anis
|
||||
|
||||
|
||||
fs=($( osascript -e "use framework \"Foundation\"
|
||||
property this : a reference to the current application
|
||||
property NSPasteboard : a reference to NSPasteboard of this
|
||||
property NSURL : a reference to NSURL of this
|
||||
property pb : a reference to NSPasteboard's generalPasteboard
|
||||
|
||||
property text item delimiters : linefeed
|
||||
|
||||
pb's readObjectsForClasses:[NSURL] options:[]
|
||||
(result's valueForKey:\"path\") as list as text" ))
|
||||
|
||||
cp -R -- "${fs[@]}" "$2/"
|
|
@ -0,0 +1,56 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: 'cd' to the directory from CDPATH
|
||||
#
|
||||
# Details: If the CDPATH environment variable is not set, the default value of
|
||||
# ${XDG_CONFIG_HOME:-$HOME/.config}/nnn/bookmarks will be used.
|
||||
# You can create this directory and fill it with symbolic links to your
|
||||
# favorite directories. It's a good idea to add it to CDPATH so that it
|
||||
# could also be used from the command line outside of nnn.
|
||||
# The fzf search is done on the directory basename (the first column).
|
||||
#
|
||||
# This plugin is an extended version of the bookmarks plugin.
|
||||
# If you set your CDPATH to ${XDG_CACHE_HOME:-$HOME/.cache}/nnn/bookmarks
|
||||
# or to the value of BOOKMARKS_DIR, you can use it as a bookmarks replacement.
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Yuri Kloubakov
|
||||
|
||||
# shellcheck disable=SC1090,SC1091
|
||||
. "$(dirname "$0")"/.nnn-plugin-helper
|
||||
|
||||
# Get a list of (symbolic links to) directories for every element of CDPATH
|
||||
get_dirs() {
|
||||
IFS=':'
|
||||
for path in $CDPATH; do
|
||||
for entry in "$path"/*; do
|
||||
if [ -d "$entry" ]; then
|
||||
name=$(basename "$entry" | grep -o '^.\{1,24\}')
|
||||
if [ -h "$entry" ]; then
|
||||
slink=$(ls -dl -- "$entry")
|
||||
entry=${slink#*" $entry -> "}
|
||||
fi
|
||||
printf "%-24s :%s\n" "${name}" "$entry"
|
||||
fi
|
||||
done
|
||||
done
|
||||
}
|
||||
|
||||
abort() {
|
||||
echo "$1"
|
||||
read -r _
|
||||
exit 1
|
||||
}
|
||||
|
||||
if [ -z "$CDPATH" ]; then
|
||||
CDPATH="${XDG_CONFIG_HOME:-$HOME/.config}/nnn/bookmarks"
|
||||
[ -d "$CDPATH" ] || abort "CDPATH is not set and there is no \"$CDPATH\" directory"
|
||||
fi
|
||||
|
||||
dir_list=$(get_dirs)
|
||||
[ -n "$dir_list" ] || abort "There are no directories to choose from. Check your \"$CDPATH\"."
|
||||
|
||||
dir=$(echo "$dir_list" | fzf --nth=1 --delimiter=':' | awk -F: 'END { print $2 }')
|
||||
if [ -n "$dir" ]; then
|
||||
nnn_cd "$dir" 0
|
||||
fi
|
|
@ -2,19 +2,23 @@
|
|||
|
||||
# Description: Create and verify checksums
|
||||
#
|
||||
# For selection: it will generate one file containing the checksums with file names
|
||||
# [and with paths if they are in another directory]
|
||||
# the output checksum filename will be checksum_timestamp.checksum_type
|
||||
# For file: if the file is a checksum, the plugin does the verification
|
||||
# Note: On macOS, install the relevant checksum packages from Homebrew with:
|
||||
# brew install coreutils
|
||||
#
|
||||
# Details:
|
||||
# - selection: it will generate one file with the checksums and filenames
|
||||
# (and with paths if they are in another directory)
|
||||
# output checksum filename format: checksum_timestamp.checksum_type
|
||||
# - file: if the file is a checksum, the plugin does the verification
|
||||
# if the file is not a checksum, checksum will be generated for it
|
||||
# the output checksum filename will be filename.checksum_type
|
||||
# For directory: recursively calculates checksum for all the files in the directory
|
||||
# - directory: recursively calculates checksum for all the files in the dir
|
||||
# the output checksum filename will be directory.checksum_type
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: ath3, Arun Prakash Jana
|
||||
# Authors: ath3, Arun Prakash Jana
|
||||
|
||||
selection=${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.selection
|
||||
selection=${NNN_SEL:-${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.selection}
|
||||
resp=f
|
||||
chsum=md5
|
||||
|
||||
|
@ -45,6 +49,11 @@ fi
|
|||
if [ "$resp" = "s" ]; then
|
||||
checksum_type
|
||||
sed 's|'"$PWD/"'||g' < "$selection" | xargs -0 -I{} ${chsum}sum {} > "checksum_$(date '+%Y%m%d%H%M').$chsum"
|
||||
|
||||
# Clear selection
|
||||
if [ -p "$NNN_PIPE" ]; then
|
||||
printf "-" > "$NNN_PIPE"
|
||||
fi
|
||||
elif [ -n "$1" ]; then
|
||||
if [ -f "$1" ]; then
|
||||
for chks in md5 sha1 sha224 sha256 sha384 sha512
|
||||
|
@ -52,7 +61,7 @@ elif [ -n "$1" ]; then
|
|||
if echo "$1" | grep -q \.${chks}$; then
|
||||
${chks}sum -c < "$1"
|
||||
read -r _
|
||||
return
|
||||
exit
|
||||
fi
|
||||
done
|
||||
checksum_type
|
||||
|
|
|
@ -0,0 +1,80 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: Add selection or hovered file/directory to cmus queue
|
||||
#
|
||||
# Dependencies: cmus, pgrep, xdotool (optional)
|
||||
#
|
||||
# Notes:
|
||||
# 1. If adding selection, files/dirs are added in the same order they were selected in nnn
|
||||
# 2. A new window will be opened if cmus is not running already, playback will start immediately
|
||||
# 3. If cmus is already running, files will be appended to the queue with no forced playback
|
||||
#
|
||||
# TODO:
|
||||
# 1. Add cava and cmus-lyrics as optional dependencies
|
||||
# 2. Start cava and/or cmus-lyrics in tmux or kitty panes next to cmus
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Kabouik
|
||||
|
||||
# (Optional) Set preferred terminal emulator for cmus if not set in your env,
|
||||
# or leave commented out to use OS default
|
||||
#TERMINAL="kitty"
|
||||
|
||||
if ! type cmus >/dev/null; then
|
||||
printf "cmus missing"
|
||||
read -r _
|
||||
exit 1
|
||||
fi
|
||||
|
||||
selection=${NNN_SEL:-${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.selection}
|
||||
|
||||
start_cmus() {
|
||||
type xdotool >/dev/null && nnnwindow="$(xdotool getactivewindow)"
|
||||
case "$TERMINAL" in
|
||||
kitty | gnome-terminal | st)
|
||||
nohup "$TERMINAL" -- cmus & ;;
|
||||
havoc)
|
||||
nohup "$TERMINAL" cmus & ;;
|
||||
"")
|
||||
nohup x-terminal-emulator -e cmus & ;;
|
||||
*)
|
||||
nohup "$TERMINAL" -e cmus & ;;
|
||||
esac
|
||||
# Give the new terminal some time to open
|
||||
until cmus-remote -C; do sleep 0.1; done
|
||||
[ -n "$nnnwindow" ] && xdotool windowactivate "$nnnwindow"
|
||||
} >/dev/null 2>&1
|
||||
|
||||
fill_queue() {
|
||||
if [ "$REPLY" = "s" ]; then
|
||||
xargs < "$selection" -0 cmus-remote -q
|
||||
elif [ -n "$1" ]; then
|
||||
cmus-remote -q "$1"
|
||||
fi
|
||||
}
|
||||
|
||||
# If active selection,then ask what to do
|
||||
if [ -s "$selection" ]; then
|
||||
printf "Queue [s]election or [c]urrently hovered? [default=c]: "
|
||||
read -r REPLY
|
||||
fi
|
||||
|
||||
# If cmus is not running, start and play queue
|
||||
if ! pgrep cmus >/dev/null; then
|
||||
printf "cmus is not running, starting it in a new %s window.\n" "$TERMINAL"
|
||||
start_cmus
|
||||
fill_queue "$1"
|
||||
cmus-remote -p
|
||||
printf "Files added to cmus queue.\n"
|
||||
else # Append to existing queue if cmus is already running
|
||||
fill_queue "$1"
|
||||
printf "Files appended to current cmus queue.\n"
|
||||
fi
|
||||
|
||||
# Change view
|
||||
cmus-remote -C "view 4"
|
||||
|
||||
# Clear selection
|
||||
if [ -p "$NNN_PIPE" ]; then
|
||||
printf "-" > "$NNN_PIPE"
|
||||
fi
|
|
@ -2,34 +2,61 @@
|
|||
|
||||
# Description: Show diff of 2 directories or multiple files in vimdiff
|
||||
#
|
||||
# Note: vim may show the warning: 'Vim: Warning: Input is not from a terminal'
|
||||
# press 'Enter' to ignore and proceed.
|
||||
# Notes:
|
||||
# 1. vim may show the warning: 'Vim: Warning: Input is not from a terminal'
|
||||
# press 'Enter' to ignore and proceed.
|
||||
# 2. if only one file is in selection, the hovered file is considered as the
|
||||
# second file to diff with
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Authors: Arun Prakash Jana, ath3
|
||||
|
||||
selection=${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.selection
|
||||
selection=${NNN_SEL:-${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.selection}
|
||||
|
||||
if type nvim >/dev/null 2>&1; then
|
||||
diffcmd="nvim -d"
|
||||
else
|
||||
diffcmd="vimdiff +0"
|
||||
fi
|
||||
|
||||
dirdiff() {
|
||||
dir1=$(mktemp "${TMPDIR:-/tmp}"/nnn-"$(basename "$1")".XXXXXXXX)
|
||||
dir2=$(mktemp "${TMPDIR:-/tmp}"/nnn-"$(basename "$2")".XXXXXXXX)
|
||||
ls -A1 "$1" > "$dir1"
|
||||
ls -A1 "$2" > "$dir2"
|
||||
$diffcmd "$dir1" "$dir2"
|
||||
rm -- "$dir1" "$dir2"
|
||||
}
|
||||
|
||||
if [ -s "$selection" ]; then
|
||||
arr=$(tr '\0' '\n' < "$selection")
|
||||
if [ "$(echo "$arr" | wc -l)" -gt 1 ]; then
|
||||
f1="$(echo "$arr" | sed -n '1p')"
|
||||
f2="$(echo "$arr" | sed -n '2p')"
|
||||
if [ -d "$f1" ] && [ -d "$f2" ]; then
|
||||
dir1=$(mktemp "${TMPDIR:-/tmp}"/nnn-"$(basename "$f1")".XXXXXXXX)
|
||||
dir2=$(mktemp "${TMPDIR:-/tmp}"/nnn-"$(basename "$f2")".XXXXXXXX)
|
||||
ls -A1 "$f1" > "$dir1"
|
||||
ls -A1 "$f2" > "$dir2"
|
||||
vimdiff "$dir1" "$dir2"
|
||||
rm "$dir1" "$dir2"
|
||||
f1="$(echo "$arr" | sed -n '1p')"
|
||||
f2="$(echo "$arr" | sed -n '2p')"
|
||||
if [ -d "$f1" ] && [ -d "$f2" ]; then
|
||||
dirdiff "$f1" "$f2"
|
||||
else
|
||||
# If xargs supports the -o option, use it to get rid of:
|
||||
# Vim: Warning: Input is not from a terminal
|
||||
# xargs -0 -o vimdiff < $selection
|
||||
|
||||
xargs -0 vimdiff +0 < "$selection"
|
||||
eval xargs -0 "$diffcmd" < "$selection"
|
||||
fi
|
||||
elif [ -n "$1" ]; then
|
||||
f1="$(echo "$arr" | sed -n '1p')"
|
||||
if [ -d "$f1" ] && [ -d "$1" ]; then
|
||||
dirdiff "$f1" "$1"
|
||||
elif [ -f "$f1" ] && [ -f "$1" ]; then
|
||||
$diffcmd "$f1" "$1"
|
||||
else
|
||||
echo "cannot compare file with directory"
|
||||
fi
|
||||
else
|
||||
echo "needs at least 2 files or directories selected for comparison"
|
||||
fi
|
||||
fi
|
||||
|
||||
# Clear selection
|
||||
if [ -p "$NNN_PIPE" ]; then
|
||||
printf "-" > "$NNN_PIPE"
|
||||
fi
|
||||
|
|
|
@ -1,23 +1,26 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: Open a Drag and drop window, to drop files onto other programs.
|
||||
# Also provides drag and drop window for files.
|
||||
# Also provides drag and drop window for files.
|
||||
#
|
||||
# Files that are dropped will be added to nnn's selection
|
||||
# Some webbased files will be downloaded to current directory with curl
|
||||
# and it may overwrite some existing files
|
||||
# Dependencies: dragon - https://github.com/mwh/dragon
|
||||
#
|
||||
# The user has to mm to clear nnn's selection first
|
||||
# Notes:
|
||||
# 1. Files that are dropped will be added to nnn's selection
|
||||
# Some web-based files will be downloaded to current dir
|
||||
# with curl and it may overwrite some existing files
|
||||
# 2. The user has to mm to clear nnn's selection first
|
||||
#
|
||||
# Dependency: https://github.com/mwh/dragon
|
||||
# Shell: POSIX compliant
|
||||
# Author: 0xACE
|
||||
|
||||
selection=${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.selection
|
||||
selection=${NNN_SEL:-${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.selection}
|
||||
resp=f
|
||||
all=
|
||||
if which dragon-drag-and-drop >/dev/null 2>&1; then
|
||||
if type dragon-drag-and-drop >/dev/null 2>&1; then
|
||||
dnd="dragon-drag-and-drop"
|
||||
elif type dragon-drop >/dev/null 2>&1; then
|
||||
dnd="dragon-drop"
|
||||
else
|
||||
dnd="dragon"
|
||||
fi
|
||||
|
|
65
plugins/dups
65
plugins/dups
|
@ -1,15 +1,70 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: List non-empty duplicate files in the current directory (based on size followed by MD5)
|
||||
# Description: List non-empty duplicates in the current dir (based on size followed by MD5)
|
||||
#
|
||||
# Source: https://www.commandlinefu.com/commands/view/3555/find-duplicate-files-based-on-size-first-then-md5-hash
|
||||
#
|
||||
# Requires: find md5sum sort uniq xargs
|
||||
# Dependencies: find md5sum sort uniq xargs gsed
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: syssyphus
|
||||
# Notes:
|
||||
# 1. If the file size exceeds $size_digits digits the file will be misplaced
|
||||
# 12 digits fit files up to 931GiB
|
||||
# 2. Bash compatible required for mktemp
|
||||
#
|
||||
# Shell: Bash
|
||||
# Authors: syssyphus, KlzXS
|
||||
|
||||
find . -size +0 -type f -printf "%s\n" | sort -rn | uniq -d | xargs -I{} -n1 find -type f -size {}c -print0 | xargs -0 md5sum | sort | uniq -w32 --all-repeated=separate
|
||||
EDITOR="${EDITOR:-vi}"
|
||||
TMPDIR="${TMPDIR:-/tmp}"
|
||||
|
||||
size_digits=12
|
||||
tmpfile=$(mktemp "$TMPDIR/.nnnXXXXXX")
|
||||
|
||||
printf "\
|
||||
## This is an overview of all duplicate files found.
|
||||
## Comment out the files you wish to remove. You will be given an option to cancel.
|
||||
## Lines with double comments (##) are ignored.
|
||||
## You will have the option to remove the files with force or interactively.\n
|
||||
" > "$tmpfile"
|
||||
|
||||
# shellcheck disable=SC2016
|
||||
find . -size +0 -type f -printf "%${size_digits}s %p\n" | sort -rn | uniq -w"${size_digits}" -D | sed -e '
|
||||
s/^ \{0,12\}\([0-9]\{0,12\}\) \(.*\)$/printf "%s %s\\n" "$(md5sum "\2")" "d\1"/
|
||||
' | tr '\n' '\0' | xargs -0 -n1 sh -c | sort | { uniq -w32 --all-repeated=separate; echo; } | sed -ne '
|
||||
h
|
||||
s/^\(.\{32\}\).* d\([0-9]*\)$/## md5sum: \1 size: \2 bytes/p
|
||||
g
|
||||
|
||||
:loop
|
||||
N
|
||||
/.*\n$/!b loop
|
||||
p' | sed -e 's/^.\{32\} \(.*\) d[0-9]*$/\1/' >> "$tmpfile"
|
||||
|
||||
"$EDITOR" "$tmpfile"
|
||||
|
||||
printf "Remove commented files? (yes/no) [default=n]: "
|
||||
read -r commented
|
||||
|
||||
if [ "$commented" = "y" ]; then
|
||||
sedcmd="/^##.*/d; /^[^#].*/d; /^$/d; s/^# *\(.*\)$/\1/"
|
||||
else
|
||||
printf "Press any key to exit"
|
||||
read -r _
|
||||
exit
|
||||
fi
|
||||
|
||||
printf "Remove with force or interactive? (f/i) [default=i]: "
|
||||
read -r force
|
||||
|
||||
if [ "$force" = "f" ]; then
|
||||
#shellcheck disable=SC2016
|
||||
sed -e "$sedcmd" "$tmpfile" | tr '\n' '\0' | xargs -0 -r sh -c 'rm -f -- "$0" "$@" </dev/tty'
|
||||
else
|
||||
#shellcheck disable=SC2016
|
||||
sed -e "$sedcmd" "$tmpfile" | tr '\n' '\0' | xargs -0 -r sh -c 'rm -i -- "$0" "$@" </dev/tty'
|
||||
fi
|
||||
|
||||
rm -- "$tmpfile"
|
||||
|
||||
printf "Press any key to exit"
|
||||
read -r _
|
||||
|
|
|
@ -0,0 +1,89 @@
|
|||
#!/usr/bin/env bash
|
||||
|
||||
# Description: Run custom search and list results in smart context
|
||||
#
|
||||
# Note: This plugin retains search history
|
||||
#
|
||||
# Usage:
|
||||
# Run plugin and enter e.g. "-size +10M" to list files in current
|
||||
# directory larger than 10M. By default entered expressions are
|
||||
# interpreted as arguments to find. Results have to be NUL
|
||||
# terminated which is done by default for find. Alternatively one
|
||||
# can prepend a '$' to run a custom search program such as fd or
|
||||
# ripgrep. Entered expressions will be saved in history file to
|
||||
# be listed as bookmarks and and can be entered by index and edited.
|
||||
#
|
||||
# Shell: Bash
|
||||
# Author: Arun Prakash Jana, Luuk van Baal
|
||||
TMPDIR="${TMPDIR:-/tmp}"
|
||||
NNN_FINDHIST="${NNN_FINDHIST:-${XDG_CONFIG_HOME:-$HOME/.config}/nnn/finderbms}"
|
||||
NNN_FINDHISTLEN="${NNN_FINDHISTLEN:-10000}"
|
||||
|
||||
printexamples() {
|
||||
printf -- "-maxdepth 1 -name pattern
|
||||
-maxdepth 1 -size +100M
|
||||
\$fd -0 pattern
|
||||
\$fd -0 -d 2 -S +100M
|
||||
\$grep -rlZ pattern
|
||||
\$rg -l0 pattern
|
||||
\$fzf -m | tr '\\\n' '\\\0'\n"
|
||||
}
|
||||
|
||||
printexprs() {
|
||||
for ((i = "$1"; i < ${#fexprs[@]}; i++)); do
|
||||
printf '%s\t%s\n' "$((i + 1))" "${fexprs[$i]}"
|
||||
done
|
||||
}
|
||||
|
||||
mapexpr() {
|
||||
if [ "$fexpr" -eq "$fexpr" ] 2>/dev/null; then
|
||||
fexpr=${fexprs[$((fexpr - 1))]}
|
||||
read -r -e -p "Search expression: " -i "$fexpr" fexpr
|
||||
else
|
||||
return 1
|
||||
fi
|
||||
}
|
||||
|
||||
readexpr() {
|
||||
case "$fexpr" in
|
||||
h) clear
|
||||
printf "Examples:\n"
|
||||
mapfile -t fexprs < <(printexamples)
|
||||
printexprs 0
|
||||
read -r -p "Search expression or index: " fexpr
|
||||
mapexpr
|
||||
[ -n "$fexpr" ] && readexpr ;;
|
||||
\$*) cmd="${fexpr:1}" ;;
|
||||
*) mapexpr && readexpr
|
||||
cmd="find . $fexpr -print0" ;;
|
||||
esac
|
||||
}
|
||||
|
||||
clear
|
||||
[ -f "$NNN_FINDHIST" ] || printexamples > "$NNN_FINDHIST"
|
||||
|
||||
mapfile -t fexprs < <(sort "$NNN_FINDHIST" | uniq -c | sort -nr | head -n5 |\
|
||||
awk '{for (i=2; i<NF; i++) printf $i " "; print $NF}')
|
||||
printf "Most used search expressions:\n"
|
||||
printexprs 0
|
||||
|
||||
mapfile -t -O"$i" fexprs < <(tac "$NNN_FINDHIST" | awk '!a[$0]++' | head -n5)
|
||||
printf "Most recently used search expressions:\n"
|
||||
printexprs "$i"
|
||||
read -r -p "Search expression or index (h for help): " fexpr
|
||||
|
||||
mapexpr
|
||||
|
||||
if [ -n "$fexpr" ]; then
|
||||
printf "+l" > "$NNN_PIPE"
|
||||
while :; do
|
||||
readexpr
|
||||
eval "$cmd" > "$NNN_PIPE" && break
|
||||
read -r -e -p "Search expression: " -i "$fexpr" fexpr
|
||||
done
|
||||
if [ -n "$fexpr" ]; then
|
||||
tail -n"$NNN_FINDHISTLEN" "$NNN_FINDHIST" > "$TMPDIR/finderbms"
|
||||
printf "%s\n" "$fexpr" >> "$TMPDIR/finderbms"
|
||||
mv -- "$TMPDIR/finderbms" "$NNN_FINDHIST"
|
||||
fi
|
||||
fi
|
|
@ -0,0 +1,75 @@
|
|||
#!/usr/bin/env bash
|
||||
|
||||
# Description: Clean filename or dirname (either hovered or selections)
|
||||
# to be more shell-friendly. This script cleans
|
||||
# non A-Za-z0-9._- characters.
|
||||
# and replaces it with underscore (_).
|
||||
#
|
||||
# It supports cleaning single/double quote, newline,
|
||||
# leading, trailing spaces.
|
||||
#
|
||||
# eg.
|
||||
# to be continued (つづく).mp4 -> to_be_continued______.mp4
|
||||
# [work] stuff.txt -> _work__stuff.txt
|
||||
# home's server -> home_s_server
|
||||
# qwe\trty -> __qwe_rty
|
||||
#
|
||||
# And if there are two almost similar filenames
|
||||
# like: 'asd]f' and 'asd f' both will be renamed to 'asd_f',
|
||||
# to avoid overwriting, the last file will be prepended by _.
|
||||
# So they will be: 'asd_f' and '_asd_f'
|
||||
#
|
||||
# Dependencies: sed
|
||||
#
|
||||
# Shell: Bash
|
||||
# Author: Benawi Adha
|
||||
|
||||
prompt=true
|
||||
sel=${NNN_SEL:-${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.selection}
|
||||
|
||||
cleanup() {
|
||||
# printf "%s" "$1" | sed -e 's/[^A-Za-z0-9._-]/_/g'
|
||||
printf "%s" "$1" | sed 's/[^A-Za-z0-9._-]/_/g' | sed ':a;N;$!ba;s/\n/_/g'
|
||||
}
|
||||
|
||||
if [ -s "$sel" ]; then
|
||||
targets=()
|
||||
while IFS= read -r -d '' i || [ -n "$i" ]; do
|
||||
targets+=( "$(basename "$i")" )
|
||||
done < "$sel"
|
||||
else
|
||||
targets=("$1")
|
||||
fi
|
||||
|
||||
for i in "${targets[@]}"; do
|
||||
printf "%s -> %s\n" "$i" "$(cleanup "$i")";
|
||||
done
|
||||
|
||||
if $prompt; then
|
||||
echo
|
||||
printf "Proceed [Yn]? "
|
||||
read -r input
|
||||
case "$input" in
|
||||
y|Y|'')
|
||||
;;
|
||||
*)
|
||||
echo "Canceled"
|
||||
exit
|
||||
;;
|
||||
esac
|
||||
fi
|
||||
|
||||
for i in "${targets[@]}"; do
|
||||
if [ "$i" != "$(cleanup "$i")" ]; then
|
||||
tmp=''
|
||||
if [ -e "$(cleanup "$i")" ]; then
|
||||
tmp='_'
|
||||
fi
|
||||
mv -- "$i" "$tmp$(cleanup "$i")";
|
||||
fi
|
||||
done
|
||||
|
||||
# Clear selection
|
||||
if [ -s "$sel" ] && [ -p "$NNN_PIPE" ]; then
|
||||
printf "-" > "$NNN_PIPE"
|
||||
fi
|
97
plugins/fzcd
97
plugins/fzcd
|
@ -1,36 +1,89 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: Run fzf/fzy, fd/fdfind/find and go to the directory of the file selected
|
||||
# Description: Fuzzy search multiple locations read-in from a path-list file
|
||||
# (or $PWD) and open the selected file's dir in a smart context.
|
||||
# Dependencies: fzf, find (only for multi-location search)
|
||||
#
|
||||
# Details: Paths in list file should be newline-separated absolute paths.
|
||||
# Paths can be file paths; the script will scan the parent dirs.
|
||||
#
|
||||
# The path-list file precedence is:
|
||||
# - "$1" (the hovered file) if it exists, is plain-text and the
|
||||
# first line points to an existing file
|
||||
# - "$LIST" if set below
|
||||
# - "$2" (the current directory) [mimics plugin fzcd behaviour]
|
||||
#
|
||||
# The path-list file can be generated easily:
|
||||
# - pick the (file)paths in picker mode to path-list file
|
||||
# - OR, edit selection in nnn and save as path-list file
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Anna Arad
|
||||
# Author: Anna Arad, Arun Prakash Jana, KlzXS
|
||||
|
||||
IFS="$(printf '\n\r')"
|
||||
|
||||
# shellcheck disable=SC1090,SC1091
|
||||
. "$(dirname "$0")"/.nnn-plugin-helper
|
||||
|
||||
if [ "$(cmd_exists fzy)" -eq "0" ]; then
|
||||
if [ "$(cmd_exists fd)" -eq "0" ]; then
|
||||
fd=fd
|
||||
elif [ "$(cmd_exists fdfind)" -eq "0" ]; then
|
||||
fd=fdfind
|
||||
else
|
||||
fd=find
|
||||
fi
|
||||
CTX=+
|
||||
LIST="${LIST:-""}"
|
||||
|
||||
sel=$($fd | fzy)
|
||||
elif [ "$(cmd_exists fzf)" -eq "0" ]; then
|
||||
sel=$(fzf)
|
||||
else
|
||||
exit 1
|
||||
if ! type fzf >/dev/null 2>&1; then
|
||||
printf "fzf missing"
|
||||
read -r _
|
||||
exit 1
|
||||
fi
|
||||
|
||||
if [ -n "$1" ] && [ "$(file -b --mime-type "$1")" = 'text/plain' ] && [ -e "$(head -1 "$1")" ]; then
|
||||
LIST="$1"
|
||||
elif ! [ -s "$LIST" ]; then
|
||||
sel=$(fzf)
|
||||
# Show only the file and parent dir
|
||||
# sel=$(fzf --delimiter / --with-nth=-2,-1 --tiebreak=begin --info=hidden)
|
||||
|
||||
LIST=''
|
||||
fi
|
||||
|
||||
if [ -n "$LIST" ]; then
|
||||
if type find >/dev/null 2>&1; then
|
||||
tmpfile=$(mktemp /tmp/abc-script.XXXXXX)
|
||||
|
||||
while IFS= read -r path; do
|
||||
if [ -d "$path" ]; then
|
||||
printf "%s\n" "$path" >> "$tmpfile"
|
||||
elif [ -f "$path" ]; then
|
||||
printf "%s\n" "$(dirname "$path")" >> "$tmpfile"
|
||||
fi
|
||||
done < "$LIST"
|
||||
|
||||
sel=$(xargs -d '\n' < "$tmpfile" -I{} find {} -type f -printf "%H//%P\n" | sed '/.*\/\/\(\..*\|.*\/\..*\)/d; s:/\+:/:g' | fzf --delimiter / --tiebreak=begin --info=hidden)
|
||||
# Alternative for 'fd'
|
||||
# sel=$(xargs -d '\n' < "$tmpfile" fd . | fzf --delimiter / --tiebreak=begin --info=hidden)
|
||||
|
||||
rm -- "$tmpfile"
|
||||
else
|
||||
printf "find missing"
|
||||
read -r _
|
||||
exit 1
|
||||
fi
|
||||
fi
|
||||
|
||||
if [ -n "$sel" ]; then
|
||||
if ! [ -d "$sel" ]; then
|
||||
sel=$(dirname "$sel")
|
||||
elif [ "$sel" = "." ]; then
|
||||
if [ "$sel" = "." ] || { ! [ -d "$sel" ] && ! [ -f "$sel" ]; }; then
|
||||
exit 0
|
||||
fi
|
||||
fi
|
||||
|
||||
# Remove "./" prefix if it exists
|
||||
sel="${sel#./}"
|
||||
nnn_cd "$PWD/$sel"
|
||||
# Check if the selected path returned by fzf command is absolute
|
||||
case $sel in
|
||||
/*) nnn_cd "$sel" "$CTX" ;;
|
||||
*)
|
||||
# Remove "./" prefix if it exists
|
||||
sel="${sel#./}"
|
||||
|
||||
if [ "$PWD" = "/" ]; then
|
||||
nnn_cd "/$sel" "$CTX"
|
||||
else
|
||||
nnn_cd "$PWD/$sel" "$CTX"
|
||||
fi;;
|
||||
esac
|
||||
fi
|
||||
|
|
|
@ -1,15 +1,17 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: Fuzzy find a command from history, edit in $EDITOR and run as a command
|
||||
# Currently supports only bash and fish history
|
||||
# Description: Fuzzy find a command from history,
|
||||
# edit in $EDITOR and run as a command
|
||||
#
|
||||
# Note: Supports only bash, zsh and fish history
|
||||
#
|
||||
# TODO: For zsh there's also $ZDOTDIR which might need to be checked as well for the -z $HISTFILE && -n $ZDOTDIR case.
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Arun Prakash Jana
|
||||
|
||||
if which fzf >/dev/null 2>&1; then
|
||||
if type fzf >/dev/null 2>&1; then
|
||||
fuzzy=fzf
|
||||
elif which fzy >/dev/null 2>&1; then
|
||||
fuzzy=fzy
|
||||
else
|
||||
exit 1
|
||||
fi
|
||||
|
@ -17,14 +19,25 @@ fi
|
|||
shellname="$(basename "$SHELL")"
|
||||
|
||||
if [ "$shellname" = "bash" ]; then
|
||||
hist_file="$HOME/.bash_history"
|
||||
if [ -f "$HISTFILE" ]; then
|
||||
hist_file="$HISTFILE"
|
||||
else
|
||||
hist_file="$HOME/.bash_history"
|
||||
fi
|
||||
entry="$("$fuzzy" < "$hist_file")"
|
||||
elif [ "$shellname" = "zsh" ]; then
|
||||
if [ -f "$HISTFILE" ]; then
|
||||
hist_file="$HISTFILE"
|
||||
else
|
||||
hist_file="$HOME/.zsh_history"
|
||||
fi
|
||||
entry="$("$fuzzy" < "$hist_file")"
|
||||
elif [ "$shellname" = "fish" ]; then
|
||||
hist_file="$HOME/.config/fish/fish_history"
|
||||
hist_file="$HOME/.local/share/fish/fish_history"
|
||||
entry="$(grep "\- cmd: " "$hist_file" | cut -c 8- | "$fuzzy")"
|
||||
fi
|
||||
|
||||
if ! [ -z "$entry" ]; then
|
||||
if [ -n "$entry" ]; then
|
||||
tmpfile=$(mktemp)
|
||||
echo "$entry" >> "$tmpfile"
|
||||
$EDITOR "$tmpfile"
|
||||
|
@ -33,7 +46,7 @@ if ! [ -z "$entry" ]; then
|
|||
$SHELL -c "$(cat "$tmpfile")"
|
||||
fi
|
||||
|
||||
rm "$tmpfile"
|
||||
rm -- "$tmpfile"
|
||||
|
||||
printf "Press any key to exit"
|
||||
read -r _
|
||||
|
|
|
@ -1,27 +1,85 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: Fuzzy find a file in directory subtree with fzy
|
||||
# Opens in $VISUAL or $EDITOR if text
|
||||
# Opens other type of files with xdg-open
|
||||
# Description: Regular mode:
|
||||
# Fuzzy find a file in directory subtree.
|
||||
# Opens in $VISUAL or $EDITOR if text.
|
||||
# Opens other type of files with xdg-open.
|
||||
# Work only with a single file selected.
|
||||
#
|
||||
# Requires: fzf/fzy, xdg-open
|
||||
# Picker mode:
|
||||
# If picker mode output file is passed, it
|
||||
# will be overwritten with any picked files.
|
||||
# Leaves untouched if no file is picked.
|
||||
# Works with single/multiple files selected.
|
||||
#
|
||||
# Dependencies: fd/find, fzf/skim, xdg-open/open (on macOS)
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Arun Prakash Jana
|
||||
|
||||
if which fzf >/dev/null 2>&1; then
|
||||
fuzzy=fzf
|
||||
elif which fzy >/dev/null 2>&1; then
|
||||
fuzzy=fzy
|
||||
NUKE="${XDG_CONFIG_HOME:-$HOME/.config}/nnn/plugins/nuke"
|
||||
USE_NUKE=0
|
||||
|
||||
# shellcheck disable=SC1090,SC1091
|
||||
. "$(dirname "$0")"/.nnn-plugin-helper
|
||||
|
||||
if type fzf >/dev/null 2>&1; then
|
||||
cmd="$FZF_DEFAULT_COMMAND"
|
||||
if type fd >/dev/null 2>&1; then
|
||||
[ -z "$cmd" ] && cmd="fd -t f 2>/dev/null"
|
||||
else
|
||||
[ -z "$cmd" ] && cmd="find . -type f 2>/dev/null"
|
||||
fi
|
||||
entry="$(eval "$cmd" | fzf -m)"
|
||||
# To show only the file name
|
||||
# entry=$(find . -type f 2>/dev/null | fzf --delimiter / --with-nth=-1 --tiebreak=begin --info=hidden)
|
||||
elif type sk >/dev/null 2>&1; then
|
||||
entry=$(find . -type f 2>/dev/null | sk)
|
||||
else
|
||||
exit 1
|
||||
fi
|
||||
|
||||
entry="$(find . -type f 2>/dev/null | "$fuzzy")"
|
||||
# Check for picker mode
|
||||
if [ "$3" ]; then
|
||||
if [ "$entry" ]; then
|
||||
case "$entry" in
|
||||
/*) fullpath="$entry" ;;
|
||||
*) fullpath="$PWD/$entry" ;;
|
||||
esac
|
||||
if [ "-" = "$3" ]; then
|
||||
printf "%s\n" "$fullpath"
|
||||
else
|
||||
printf "%s\n" "$fullpath" > "$3"
|
||||
fi
|
||||
|
||||
case "$(file -biL "$entry")" in
|
||||
*text*)
|
||||
"${VISUAL:-$EDITOR}" "$entry" ;;
|
||||
*)
|
||||
xdg-open "$entry" >/dev/null 2>&1 ;;
|
||||
esac
|
||||
# Tell `nnn` to clear its internal selection
|
||||
printf "%s" "0p" > "$NNN_PIPE"
|
||||
fi
|
||||
|
||||
exit 0
|
||||
fi
|
||||
|
||||
if [ "$entry" ]; then
|
||||
if [ "$USE_NUKE" -ne 0 ]; then
|
||||
"$NUKE" "$entry"
|
||||
exit 0
|
||||
fi
|
||||
|
||||
# Open the file (works for a single file only)
|
||||
cmd_file=""
|
||||
cmd_open=""
|
||||
if uname | grep -q "Darwin"; then
|
||||
cmd_file="file -bIL"
|
||||
cmd_open="open"
|
||||
else
|
||||
cmd_file="file -biL"
|
||||
cmd_open="xdg-open"
|
||||
fi
|
||||
|
||||
case "$($cmd_file "$entry")" in
|
||||
*text*)
|
||||
"${VISUAL:-$EDITOR}" "$entry" ;;
|
||||
*)
|
||||
$cmd_open "$entry" >/dev/null 2>&1 ;;
|
||||
esac
|
||||
fi
|
||||
|
|
|
@ -0,0 +1,59 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: Fuzzy find and execute nnn plugins (and optionally,
|
||||
# custom scripts located elsewhere).
|
||||
# Description and details of plugins can be previewed
|
||||
# from the fzf interface. Use `?` to toggle preview
|
||||
# pane on and off, ^Up/^Dn to scroll.
|
||||
#
|
||||
# Dependencies: find, fzf, cat (or bat, if installed)
|
||||
#
|
||||
# Note: For better compatibility with as many nnn plugins as possible,
|
||||
# fzplug will first execute the chosen script on the file hovered
|
||||
# in nnn, and upon failure, try to run it with no target (i.e on
|
||||
# an active selection, if present).
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Kabouik
|
||||
|
||||
# Optional scripts sources
|
||||
|
||||
# Leave blank or fill with the absolute path of a folder containing executable
|
||||
# scripts other than nnn plugins (e.g., "$HOME/.local/share/nautilus/scripts",
|
||||
# since there are numerous Nautilus script git repositories).
|
||||
# Add extra variables if needed, make sure you call them in the find command.
|
||||
|
||||
#CUSTOMDIR1="$HOME/.local/share/nautilus/scripts"
|
||||
CUSTOMDIR1=""
|
||||
CUSTOMDIR2=""
|
||||
|
||||
nnnpluginsdir="$HOME/.config/nnn/plugins"
|
||||
|
||||
# Preview with bat if installed
|
||||
if type bat >/dev/null; then
|
||||
BAT="bat --terminal-width='$(tput cols)' --decorations=always --color=always --style='${BAT_STYLE:-header,numbers}'"
|
||||
fi
|
||||
|
||||
plugin=$(find "$nnnpluginsdir" "$CUSTOMDIR1" "$CUSTOMDIR2" \
|
||||
-maxdepth 3 -perm -111 -type f 2>/dev/null | fzf --ansi --preview \
|
||||
"${BAT:-cat} {}" --preview-window="right:66%:wrap" --delimiter / \
|
||||
--with-nth -1 --bind="?:toggle-preview")
|
||||
|
||||
# Try running the script on the hovered file, and abort
|
||||
# abort if no plugin was selected (ESC or ^C pressed).
|
||||
err=0
|
||||
if ! [ "$plugin" = "" ]; then
|
||||
"$plugin" "$1" || err=1
|
||||
fi
|
||||
|
||||
# If attempt with hovered file fails, try without any target
|
||||
# (nnn selections should still be passed to the script in that case)
|
||||
if [ "$err" -eq "1" ]; then
|
||||
clear && "$plugin" || err=2
|
||||
fi
|
||||
|
||||
# Abort and show error if both fail
|
||||
if [ "$err" -eq "2" ]; then
|
||||
sep="\n---\n"
|
||||
printf "$sep""Failed to execute '%s'. See error above or try without fzfplug. Press return to continue. " "$plugin" && read -r _ && clear
|
||||
fi
|
|
@ -1,43 +1,45 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: Update nnn plugins
|
||||
# Description: Update nnn plugins to installed nnn version
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Arun Prakash Jana, KlzXS
|
||||
# Authors: Arun Prakash Jana, KlzXS
|
||||
|
||||
CONFIG_DIR=${XDG_CONFIG_HOME:-$HOME/.config}/nnn/
|
||||
PLUGIN_DIR=${XDG_CONFIG_HOME:-$HOME/.config}/nnn/plugins
|
||||
|
||||
is_cmd_exists () {
|
||||
which "$1" > /dev/null 2>&1
|
||||
echo $?
|
||||
}
|
||||
|
||||
merge () {
|
||||
vimdiff +0 "$1" "$2"
|
||||
if type nvim >/dev/null 2>&1; then
|
||||
nvim -d "$1" "$2"
|
||||
else
|
||||
vimdiff +0 "$1" "$2"
|
||||
fi
|
||||
}
|
||||
|
||||
prompt () {
|
||||
printf "%s" "Plugin $1 already exists and is different.\n"
|
||||
printf "%s\n" "Plugin $1 already exists and is different."
|
||||
printf "Keep (k), merge (m), overwrite (o) [default: k]? "
|
||||
read -r operation
|
||||
|
||||
if [ "$operation" = "m" ]; then
|
||||
op="merge"
|
||||
elif [ "$operation" = "o" ]; then
|
||||
op="cp -vRf"
|
||||
op="cp -vRf --"
|
||||
else
|
||||
op="true"
|
||||
fi
|
||||
}
|
||||
|
||||
# if [ "$(is_cmd_exists sudo)" -eq "0" ]; then
|
||||
# sucmd=sudo
|
||||
# elif [ "$(is_cmd_exists doas)" -eq "0" ]; then
|
||||
# sucmd=doas
|
||||
# else
|
||||
# sucmd=: # noop
|
||||
# fi
|
||||
if [ "$1" = "master" ] ; then
|
||||
VER="master"
|
||||
ARCHIVE_URL=https://github.com/jarun/nnn/archive/master.tar.gz
|
||||
elif type nnn >/dev/null 2>&1; then
|
||||
VER=$(nnn -V)
|
||||
ARCHIVE_URL=https://github.com/jarun/nnn/releases/download/v"$VER"/nnn-v"$VER".tar.gz
|
||||
else
|
||||
echo "nnn is not installed"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
# backup any earlier plugins
|
||||
if [ -d "$PLUGIN_DIR" ]; then
|
||||
|
@ -46,10 +48,10 @@ fi
|
|||
|
||||
mkdir -p "$PLUGIN_DIR"
|
||||
cd "$CONFIG_DIR" || exit 1
|
||||
curl -Ls -O https://github.com/jarun/nnn/archive/master.tar.gz
|
||||
tar -zxf master.tar.gz
|
||||
curl -Ls "$ARCHIVE_URL" -o nnn-"$VER".tar.gz
|
||||
tar -zxf nnn-"$VER".tar.gz
|
||||
|
||||
cd nnn-master/plugins || exit 1
|
||||
cd nnn-"$VER"/plugins || exit 1
|
||||
|
||||
# shellcheck disable=SC2044
|
||||
# We do not use obnoxious names for plugins
|
||||
|
@ -60,9 +62,9 @@ for f in $(find . -maxdepth 1 \( ! -iname "." ! -iname "*.md" \)); do
|
|||
$op "$f" ../../plugins/
|
||||
fi
|
||||
else
|
||||
cp -vRf "$f" ../../plugins/
|
||||
cp -vRf -- "$f" ../../plugins/
|
||||
fi
|
||||
done
|
||||
cd ../.. || exit 1
|
||||
|
||||
rm -rf nnn-master/ master.tar.gz
|
||||
rm -rf nnn-"$VER"/ nnn-"$VER".tar.gz
|
||||
|
|
|
@ -0,0 +1,15 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: cd to the top level of the current git repository in the current context
|
||||
# Dependencies: git
|
||||
# Shell: sh
|
||||
# Author: https://github.com/PatrickF1
|
||||
|
||||
root="$(git rev-parse --show-toplevel 2>/dev/null)"
|
||||
if [ -n "$root" ]; then
|
||||
printf "%s" "0c$root" > "$NNN_PIPE"
|
||||
else
|
||||
printf "Not in a git repository"
|
||||
read -r _
|
||||
exit 1
|
||||
fi
|
|
@ -0,0 +1,28 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: Decrypts selected files using gpg. The contents of the
|
||||
# decrypted file are stored in a file with extension .dec
|
||||
#
|
||||
# Note: If an appropriate private key cannot be found gpg silently
|
||||
# prints a message in the background and no files are written.
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: KlzXS
|
||||
|
||||
selection=${NNN_SEL:-${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.selection}
|
||||
|
||||
printf "(s)election/(c)urrent? [default=c] "
|
||||
read -r resp
|
||||
|
||||
if [ "$resp" = "s" ]; then
|
||||
files=$(tr '\0' '\n' < "$selection")
|
||||
else
|
||||
files=$1
|
||||
fi
|
||||
|
||||
printf "%s" "$files" | xargs -n1 -I{} gpg --decrypt --output "{}.dec" {}
|
||||
|
||||
# Clear selection
|
||||
if [ "$resp" = "s" ] && [ -p "$NNN_PIPE" ]; then
|
||||
printf "-" > "$NNN_PIPE"
|
||||
fi
|
|
@ -0,0 +1,45 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: Encrypts selected files using gpg. Can encrypt
|
||||
# asymmetrically (key) or symmetrically (passphrase).
|
||||
# If asymmetric encryption is chosen a key can be
|
||||
# chosen from the list of capable public keys using fzf.
|
||||
#
|
||||
# Note: Symmetric encryption only works for a single (current) file as per gpg limitations
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: KlzXS
|
||||
|
||||
# shellcheck disable=SC1090,SC1091
|
||||
. "$(dirname "$0")"/.nnn-plugin-helper
|
||||
|
||||
printf "(s)ymmetric, (a)symmetric? [default=a] "
|
||||
read -r symmetry
|
||||
|
||||
if [ "$symmetry" = "s" ]; then
|
||||
gpg --symmetric "$1"
|
||||
else
|
||||
if nnn_use_selection; then
|
||||
clear_sel=1
|
||||
# shellcheck disable=SC2154
|
||||
files=$(tr '\0' '\n' < "$selection")
|
||||
else
|
||||
clear_sel=0
|
||||
files=$1
|
||||
fi
|
||||
|
||||
keyids=$(gpg --list-public-keys --with-colons | grep -E "pub:(.*:){10}.*[eE].*:" | awk -F ":" '{print $5}')
|
||||
|
||||
#awk needs literal $10
|
||||
#shellcheck disable=SC2016
|
||||
keyuids=$(printf "%s" "$keyids" | xargs -n1 -I{} sh -c 'gpg --list-key --with-colons "{}" | grep "uid" | awk -F ":" '\''{printf "%s %s\n", "{}", $10}'\''')
|
||||
|
||||
recipient=$(printf "%s" "$keyuids" | fzf | awk '{print $1}')
|
||||
|
||||
printf "%s" "$files" | xargs -n1 gpg --encrypt --recipient "$recipient"
|
||||
|
||||
# Clear selection
|
||||
if [ "$clear_sel" -eq 1 ] && [ -p "$NNN_PIPE" ]; then
|
||||
printf "-" > "$NNN_PIPE"
|
||||
fi
|
||||
fi
|
|
@ -0,0 +1,21 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
#set -x
|
||||
# Description: Send the selected (or hovered) files to your Android device using gsconnect daemon.js.
|
||||
# GSConnect must be configured on the Android device and the PC.
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Darukutsu
|
||||
selection=${NNN_SEL:-${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.selection}
|
||||
gsconnect=$HOME/.local/share/gnome-shell/extensions/gsconnect@andyholmes.github.io/service/daemon.js
|
||||
ids=$($gsconnect -l)
|
||||
|
||||
for id in $ids; do
|
||||
if [ -s "$selection" ]; then
|
||||
xargs -0 < "$selection" -I{} "$gsconnect" -d "$id" --share-file="{}"
|
||||
# Clear selection
|
||||
printf "-" > "$NNN_PIPE"
|
||||
else
|
||||
"$gsconnect" -d "$id" --share-file="$2/$1"
|
||||
fi
|
||||
done
|
|
@ -6,7 +6,7 @@
|
|||
# Details: Set the variable EBOOK_ID to download in html format and read in w3m.
|
||||
# Clear EBOOK_ID to browse available ebooks by popularity and set it to
|
||||
# the ID once you find an interesting one.
|
||||
# To dowload and read in epub format set READER to an epub reader like
|
||||
# To download and read in epub format set READER to an epub reader like
|
||||
# epr: https://github.com/wustho/epr
|
||||
#
|
||||
# More on EBOOK_ID:
|
||||
|
@ -18,11 +18,11 @@
|
|||
# Shell: POSIX compliant
|
||||
# Author: Arun Prakash Jana
|
||||
|
||||
EBOOK_ID=
|
||||
EBOOK_ID="${EBOOK_ID:-""}"
|
||||
DIR="${XDG_CACHE_HOME:-$HOME/.cache}/nnn/gutenbooks/$EBOOK_ID"
|
||||
BROWSE_LINK="http://www.gutenberg.org/ebooks/search/?sort_order=downloads"
|
||||
BROWSER=w3m
|
||||
READER=
|
||||
BROWSE_LINK="https://www.gutenberg.org/ebooks/search/?sort_order=downloads"
|
||||
BROWSER="${BROWSER:-w3m}"
|
||||
READER="${READER:-""}"
|
||||
|
||||
if [ -n "$EBOOK_ID" ]; then
|
||||
if [ ! -e "$DIR" ]; then
|
||||
|
@ -33,7 +33,7 @@ if [ -n "$EBOOK_ID" ]; then
|
|||
curl -L -O "https://www.gutenberg.org/files/$EBOOK_ID/$EBOOK_ID-h.zip"
|
||||
unzip "$EBOOK_ID"-h.zip
|
||||
else
|
||||
curl -L -o "$EBOOK_ID".epub "http://www.gutenberg.org/ebooks/$EBOOK_ID.epub.noimages"
|
||||
curl -L -o "$EBOOK_ID".epub "https://www.gutenberg.org/ebooks/$EBOOK_ID.epub.noimages"
|
||||
fi
|
||||
fi
|
||||
|
||||
|
|
|
@ -1,11 +0,0 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: View a file in hex
|
||||
# Requires: xxd and $PAGER
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Arun Prakash Jana
|
||||
|
||||
if ! [ -z "$1" ]; then
|
||||
xxd "$1" | $PAGER
|
||||
fi
|
|
@ -1,30 +1,31 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: Resize images in a directory to screen resolution with imgp
|
||||
# imgp homepage: https://github.com/jarun/imgp
|
||||
#
|
||||
# Dependencipes: imgp - https://github.com/jarun/imgp
|
||||
#
|
||||
# Notes:
|
||||
# 1. Set res if you don't want to be prompted for desktop resolution every time
|
||||
# 2. minsize is set to 1MB by default, adjust it if you want
|
||||
# 3. imgp options used:
|
||||
# a - adaptive mode
|
||||
# c - convert PNG to JPG
|
||||
# k - skip images matching specified hres/vres
|
||||
# 1. Set res to avoid the desktop resolution prompt each time
|
||||
# 2. MINSIZE is set to 1MB by default, adjust it if you want
|
||||
# 3. imgp options used:
|
||||
# a - adaptive mode
|
||||
# c - convert PNG to JPG
|
||||
# k - skip images matching specified hres/vres
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Arun Prakash Jana
|
||||
|
||||
# set resolution (e.g. 1920x1080)
|
||||
res=
|
||||
res="${RESOLUTION}"
|
||||
|
||||
# set minimum image size (in bytes) to resize (default: 1MB)
|
||||
minsize=1048576
|
||||
MINSIZE="${MINSIZE:-1048576}"
|
||||
|
||||
if [ -z "$res" ]; then
|
||||
printf "desktop resolution (hxv): "
|
||||
read -r res
|
||||
fi
|
||||
|
||||
if ! [ -z "$res" ] && ! [ -z "$minsize" ]; then
|
||||
imgp -ackx "$res" -s "$minsize"
|
||||
if [ -n "$res" ] && [ -n "$MINSIZE" ]; then
|
||||
imgp -ackx "$res" -s "$MINSIZE"
|
||||
fi
|
||||
|
|
|
@ -1,17 +0,0 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: View thumbnail of an image or a directory of images with lsix
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Arun Prakash Jana
|
||||
|
||||
if ! [ -z "$1" ]; then
|
||||
if [ -d "$1" ]; then
|
||||
lsix "$1"/*
|
||||
else
|
||||
lsix "$1"
|
||||
fi
|
||||
|
||||
printf "Press any key to exit..."
|
||||
read -r _
|
||||
fi
|
|
@ -28,11 +28,11 @@
|
|||
##########################################################################
|
||||
|
||||
# https://github.com/jomo/imgur-screenshot
|
||||
# https://imgur.com/tools
|
||||
# https://help.imgur.com/hc/en-us/articles/209592766-Tools-for-Imgur
|
||||
#
|
||||
# Slightly modified for `nnn` integration
|
||||
#
|
||||
# Shell: bash
|
||||
# Shell: Bash
|
||||
# Description: Upload an image file to imgur
|
||||
|
||||
if [ "${1}" = "--debug" ]; then
|
||||
|
@ -112,28 +112,29 @@ check_update="true"
|
|||
|
||||
settings_path="${HOME}/.config/imgur-screenshot/settings.conf"
|
||||
if [ -f "${settings_path}" ]; then
|
||||
# shellcheck disable=SC1090
|
||||
source "${settings_path}"
|
||||
fi
|
||||
|
||||
# dependency check
|
||||
if [ "${1}" = "--check" ]; then
|
||||
(which grep &>/dev/null && echo "OK: found grep") || echo "ERROR: grep not found"
|
||||
(type grep &>/dev/null && echo "OK: found grep") || echo "ERROR: grep not found"
|
||||
if is_mac; then
|
||||
if which growlnotify &>/dev/null; then
|
||||
if type growlnotify &>/dev/null; then
|
||||
echo "OK: found growlnotify"
|
||||
elif which terminal-notifier &>/dev/null; then
|
||||
elif type terminal-notifier &>/dev/null; then
|
||||
echo "OK: found terminal-notifier"
|
||||
else
|
||||
echo "ERROR: growlnotify nor terminal-notifier found"
|
||||
fi
|
||||
(which screencapture &>/dev/null && echo "OK: found screencapture") || echo "ERROR: screencapture not found"
|
||||
(which pbcopy &>/dev/null && echo "OK: found pbcopy") || echo "ERROR: pbcopy not found"
|
||||
(type screencapture &>/dev/null && echo "OK: found screencapture") || echo "ERROR: screencapture not found"
|
||||
(type pbcopy &>/dev/null && echo "OK: found pbcopy") || echo "ERROR: pbcopy not found"
|
||||
else
|
||||
(which notify-send &>/dev/null && echo "OK: found notify-send") || echo "ERROR: notify-send (from libnotify-bin) not found"
|
||||
(which scrot &>/dev/null && echo "OK: found scrot") || echo "ERROR: scrot not found"
|
||||
(which xclip &>/dev/null && echo "OK: found xclip") || echo "ERROR: xclip not found"
|
||||
(type notify-send &>/dev/null && echo "OK: found notify-send") || echo "ERROR: notify-send (from libnotify-bin) not found"
|
||||
(type scrot &>/dev/null && echo "OK: found scrot") || echo "ERROR: scrot not found"
|
||||
(type xclip &>/dev/null && echo "OK: found xclip") || echo "ERROR: xclip not found"
|
||||
fi
|
||||
(which curl &>/dev/null && echo "OK: found curl") || echo "ERROR: curl not found"
|
||||
(type curl &>/dev/null && echo "OK: found curl") || echo "ERROR: curl not found"
|
||||
exit 0
|
||||
fi
|
||||
|
||||
|
@ -141,7 +142,7 @@ fi
|
|||
# notify <'ok'|'error'> <title> <text>
|
||||
function notify() {
|
||||
if is_mac; then
|
||||
if which growlnotify &>/dev/null; then
|
||||
if type growlnotify &>/dev/null; then
|
||||
growlnotify --icon "${imgur_icon_path}" --iconpath "${imgur_icon_path}" --title "${2}" --message "${3}"
|
||||
else
|
||||
terminal-notifier -appIcon "${imgur_icon_path}" -contentImage "${imgur_icon_path}" -title "imgur: ${2}" -message "${3}"
|
||||
|
@ -172,8 +173,8 @@ function take_screenshot() {
|
|||
function check_for_update() {
|
||||
# exit non-zero on HTTP error, output only the body (no stats) but output errors, follow redirects, output everything to stdout
|
||||
remote_version="$(curl --compressed -fsSL --stderr - "https://api.github.com/repos/jomo/imgur-screenshot/releases" | grep -Em 1 --color 'tag_name":\s*".*"' | cut -d '"' -f 4)"
|
||||
if ! [ -z "$remote_version" ]; then
|
||||
if [ ! "${current_version}" = "${remote_version}" ] && [ ! -z "${current_version}" ] && [ ! -z "${remote_version}" ]; then
|
||||
if [ -n "$remote_version" ]; then
|
||||
if [ ! "${current_version}" = "${remote_version}" ] && [ -n "${current_version}" ] && [ -n "${remote_version}" ]; then
|
||||
echo "Update found!"
|
||||
echo "Version ${remote_version} is available (You have ${current_version})"
|
||||
notify ok "Update found" "Version ${remote_version} is available (You have ${current_version}). https://github.com/jomo/imgur-screenshot"
|
||||
|
@ -204,12 +205,13 @@ function load_access_token() {
|
|||
token_expire_time=0
|
||||
# check for saved access_token and its expiration date
|
||||
if [ -f "${credentials_file}" ]; then
|
||||
# shellcheck disable=SC1090
|
||||
source "${credentials_file}"
|
||||
fi
|
||||
current_time="$(date +%s)"
|
||||
preemptive_refresh_time="$((10*60))"
|
||||
expired="$((current_time > (token_expire_time - preemptive_refresh_time)))"
|
||||
if [ ! -z "${refresh_token}" ]; then
|
||||
if [ -n "${refresh_token}" ]; then
|
||||
# token already set
|
||||
if [ "${expired}" -eq "0" ]; then
|
||||
# token expired
|
||||
|
@ -320,7 +322,7 @@ function upload_authenticated_image() {
|
|||
img_ext="$(grep -Eo '"link":\s*"[^"]+"' <<<"${response}" | cut -d "\"" -f 4 | rev | cut -d "." -f 1 | rev)" # "link" itself has ugly '\/' escaping and no https!
|
||||
del_id="$(grep -Eo '"deletehash":\s*"[^"]+"' <<<"${response}" | cut -d "\"" -f 4)"
|
||||
|
||||
if [ ! -z "${auto_delete}" ]; then
|
||||
if [ -n "${auto_delete}" ]; then
|
||||
export -f delete_image
|
||||
echo "Deleting image in ${auto_delete} seconds."
|
||||
nohup /bin/bash -c "sleep ${auto_delete} && delete_image ${imgur_anon_id} ${del_id} ${log_file}" &
|
||||
|
@ -348,7 +350,7 @@ function upload_anonymous_image() {
|
|||
img_ext="$(grep -Eo '"link":\s*"[^"]+"' <<<"${response}" | cut -d "\"" -f 4 | rev | cut -d "." -f 1 | rev)" # "link" itself has ugly '\/' escaping and no https!
|
||||
del_id="$(grep -Eo '"deletehash":\s*"[^"]+"' <<<"${response}" | cut -d "\"" -f 4)"
|
||||
|
||||
if [ ! -z "${auto_delete}" ]; then
|
||||
if [ -n "${auto_delete}" ]; then
|
||||
export -f delete_image
|
||||
echo "Deleting image in ${auto_delete} seconds."
|
||||
nohup /bin/bash -c "sleep ${auto_delete} && delete_image ${imgur_anon_id} ${del_id} ${log_file}" &
|
||||
|
@ -521,7 +523,7 @@ if [ -n "${album_title}" ]; then
|
|||
echo "Album '${album_title}' successfully created"
|
||||
album_id="$(grep -Eo '"id":\s*"[^"]+"' <<<"${response}" | cut -d "\"" -f 4)"
|
||||
del_id="$(grep -Eo '"deletehash":\s*"[^"]+"' <<<"${response}" | cut -d "\"" -f 4)"
|
||||
handle_album_creation_success "http://imgur.com/a/${album_id}" "${del_id}" "${album_title}"
|
||||
handle_album_creation_success "https://imgur.com/a/${album_id}" "${del_id}" "${album_title}"
|
||||
|
||||
if [ "${login}" = "false" ]; then
|
||||
album_id="${del_id}"
|
||||
|
@ -581,7 +583,7 @@ for upload_file in "${upload_files[@]}"; do
|
|||
# delete file if configured
|
||||
if [ "${keep_file}" = "false" ] && [ -z "${1}" ]; then
|
||||
echo "Deleting temp file ${file_dir}/${img_file}"
|
||||
rm -rf "${img_file}"
|
||||
rm -rf -- "${img_file}"
|
||||
fi
|
||||
|
||||
echo ""
|
||||
|
|
122
plugins/imgview
122
plugins/imgview
|
@ -1,27 +1,113 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: Open images in hovered directory and thumbnails
|
||||
# open hovered image in sxiv or viu and browse other images in the directory
|
||||
# Description: Open hovered or current directory in image viewer.
|
||||
# Generates media thumbnails with optional dependencies.
|
||||
#
|
||||
# Dependencies:
|
||||
# - imv (https://github.com/eXeC64/imv) or,
|
||||
# - sxiv (https://github.com/muennich/sxiv) or,
|
||||
# - nsxiv (https://codeberg.org/nsxiv/nsxiv) or,
|
||||
# - ucollage (https://github.com/ckardaris/ucollage) or,
|
||||
# - lsix (https://github.com/hackerb9/lsix), or
|
||||
# - viu (https://github.com/atanunq/viu), or
|
||||
# - catimg (https://github.com/posva/catimg), or
|
||||
# - optional: ffmpeg for audio thumbnails (album art)
|
||||
# - optional: ffmpegthumbnailer for video thumbnails
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Arun Prakash Jana
|
||||
# Author: Arun Prakash Jana, Luuk van Baal
|
||||
#
|
||||
# Consider setting NNN_PREVIEWDIR to $XDG_CACHE_HOME/nnn/previews
|
||||
# if you want to keep media thumbnails on disk between reboots.
|
||||
NNN_PREVIEWDIR="${NNN_PREVIEWDIR:-${TMPDIR:-/tmp}/nnn/previews}"
|
||||
|
||||
if [ -z "$1" ] || ! [ -s "$1" ]; then
|
||||
printf "empty file"
|
||||
read -r _
|
||||
exit 1
|
||||
fi
|
||||
exit_prompt() {
|
||||
[ -n "$1" ] && printf "%s\n" "$1"
|
||||
printf "%s" "Press any key to exit..."
|
||||
cfg=$(stty -g); stty raw -echo; head -c 1; stty "$cfg"
|
||||
clear
|
||||
exit
|
||||
}
|
||||
|
||||
if command -v sxiv >/dev/null 2>&1; then
|
||||
if [ -f "$1" ]; then
|
||||
sxiv -q "$1" "$PWD"
|
||||
elif [ -d "$1" ] || [ -h "$1" ]; then
|
||||
sxiv -qt "$1"
|
||||
make_thumbs() {
|
||||
mkdir -p "$NNN_PREVIEWDIR$dir" || return
|
||||
if [ "$1" = "viu" ] || [ "$1" = "catimg" ]; then
|
||||
[ -d "$target" ] && exit_prompt "$1 can only display a single image"
|
||||
mime="$(file -bL --mime-type -- "$target")"
|
||||
case "$mime" in
|
||||
audio/*) ffmpeg -i "$target" "$NNN_PREVIEWDIR$target.jpg" -y >/dev/null 2>&1
|
||||
ret="$NNN_PREVIEWDIR/$target.jpg" ;;
|
||||
video/*) ffmpegthumbnailer -i "$target" -o "$NNN_PREVIEWDIR$target.jpg" 2> /dev/null
|
||||
ret="$NNN_PREVIEWDIR/$target.jpg" ;;
|
||||
*) ret="$target" ;;
|
||||
esac
|
||||
fi
|
||||
elif command -v viu >/dev/null 2>&1; then
|
||||
viu -n "$1" | less -R
|
||||
for file in "$dir"/*; do
|
||||
if [ ! -f "$NNN_PREVIEWDIR$file.jpg" ]; then
|
||||
case "$(file -bL --mime-type -- "$file")" in
|
||||
audio/*) [ "$1" != "sxiv" ] &&
|
||||
ffmpeg -i "$file" "$NNN_PREVIEWDIR$file.jpg" -y >/dev/null 2>&1 ;;
|
||||
video/*) [ "$1" != "ucollage" ] &&
|
||||
ffmpegthumbnailer -i "$file" -o "$NNN_PREVIEWDIR$file.jpg" 2> /dev/null ;;
|
||||
esac
|
||||
fi
|
||||
done
|
||||
for file in "$NNN_PREVIEWDIR$dir"/*; do
|
||||
filename="$(basename "$file" .jpg)"
|
||||
[ ! -e "$dir/$filename" ] && rm -- "$file" 2>/dev/null
|
||||
done
|
||||
}
|
||||
|
||||
listimages() {
|
||||
find -L "$dir" "$NNN_PREVIEWDIR$dir" -maxdepth 1 -type f -print0 2>/dev/null | sort -z
|
||||
}
|
||||
|
||||
view_files() {
|
||||
[ -f "$target" ] && count="-n $(listimages | grep -a -m 1 -ZznF "$target" | cut -d: -f1)"
|
||||
case "$1" in
|
||||
nsxiv) listimages | xargs -0 nsxiv -a "${count:--t}" -- ;;
|
||||
sxiv) listimages | xargs -0 sxiv -a "${count:--t}" -- ;;
|
||||
imv*) listimages | xargs -0 "$1" "${count:-}" -- ;;
|
||||
esac
|
||||
}
|
||||
|
||||
target="$(readlink -f "$1")"
|
||||
[ -d "$target" ] && dir="$target" || dir="${target%/*}"
|
||||
if uname | grep -q "Darwin"; then
|
||||
[ -f "$1" ] && open "$1" >/dev/null 2>&1 &
|
||||
elif type lsix >/dev/null 2>&1; then
|
||||
if [ -d "$target" ]; then
|
||||
cd "$target" || exit_prompt
|
||||
fi
|
||||
make_thumbs lsix
|
||||
clear
|
||||
lsix
|
||||
cd "$NNN_PREVIEWDIR$dir" && lsix
|
||||
exit_prompt
|
||||
elif type ucollage >/dev/null 2>&1; then
|
||||
type ffmpeg >/dev/null 2>&1 && make_thumbs ucollage
|
||||
UCOLLAGE_EXPAND_DIRS=1 ucollage "$dir" "$NNN_PREVIEWDIR$dir" || exit_prompt
|
||||
elif type sxiv >/dev/null 2>&1; then
|
||||
type ffmpegthumbnailer >/dev/null 2>&1 && make_thumbs sxiv
|
||||
view_files sxiv >/dev/null 2>&1 &
|
||||
elif type nsxiv >/dev/null 2>&1; then
|
||||
type ffmpegthumbnailer >/dev/null 2>&1 && make_thumbs sxiv
|
||||
view_files nsxiv >/dev/null 2>&1 &
|
||||
elif type imv >/dev/null 2>&1; then
|
||||
make_thumbs imv
|
||||
view_files imv >/dev/null 2>&1 &
|
||||
elif type imvr >/dev/null 2>&1; then
|
||||
make_thumbs imv
|
||||
view_files imvr >/dev/null 2>&1 &
|
||||
elif type viu >/dev/null 2>&1; then
|
||||
clear
|
||||
make_thumbs viu
|
||||
viu -n "$ret"
|
||||
exit_prompt
|
||||
elif type catimg >/dev/null 2>&1; then
|
||||
make_thumbs catimg
|
||||
catimg "$ret"
|
||||
exit_prompt
|
||||
else
|
||||
printf "install sxiv or viu"
|
||||
read -r _
|
||||
exit 2
|
||||
exit_prompt "Please install sxiv/nsxiv/imv/viu/catimg/lsix."
|
||||
fi
|
||||
|
|
|
@ -1,17 +1,66 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: Send the selected files to your Android device using kdeconnect-cli. You must have installed and configured kdeconnect both on the Android device and on the PC.
|
||||
# Description: Send files or folders to your Android device using kdeconnect-cli.
|
||||
# kdeconnect must be configured on the Android device and the PC.
|
||||
#
|
||||
# Usage:
|
||||
# - Hover over a file or a folder and call the plugin.
|
||||
# - Alternatively, select the files and folders you would like to send, and activate the plugin.
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: juacq97
|
||||
# Author: juacq97, raffaem, N-R-K
|
||||
|
||||
SELECTION=${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.selection
|
||||
# If you want system notification, put this equal to 1
|
||||
notify=0
|
||||
|
||||
id=$(kdeconnect-cli -a --id-only | awk '{print $1}')
|
||||
if [ "$(find "$SELECTION")" ]; then
|
||||
kdeconnect-cli -d "$id" --share "$(cat "$SELECTION")"
|
||||
# If you want a system notification, uncomment the next 3 lines.
|
||||
# notify-send -a "Kdeconnect" "Sending $(cat "$SELECTION")"
|
||||
#else
|
||||
# notify-send -a "Kdeconnect" "No file selected"
|
||||
note() {
|
||||
if [ $notify = 1 ]; then
|
||||
notify-send -a "Kdeconnect" "$1"
|
||||
else
|
||||
echo "[Kdeconnect] $1"
|
||||
fi
|
||||
}
|
||||
|
||||
# kdeconnect doesn't cope with non-files
|
||||
filter_files() {
|
||||
xargs -0 -I{} sh -c '
|
||||
if [ -f "{}" ]; then
|
||||
printf "%s\0" "{}";
|
||||
else
|
||||
printf "Error: not a regular file: %s\n" "{}" >&2;
|
||||
fi;'
|
||||
}
|
||||
|
||||
send() {
|
||||
filter_files | xargs -0 -I{} kdeconnect-cli --name "$devname" --share {}
|
||||
note "Files sent"
|
||||
}
|
||||
|
||||
# Select paired device
|
||||
names=$(kdeconnect-cli --list-available --name-only 2>/dev/null)
|
||||
if [ -z "$names" ]; then
|
||||
note "No devices paired and available"
|
||||
exit
|
||||
fi
|
||||
|
||||
ndevs=$(printf "%s" "$names" | awk 'END{print NR}')
|
||||
if [ "$ndevs" -eq 1 ]; then
|
||||
devname="$names"
|
||||
else
|
||||
printf "%s" "$names" | awk '{ print NR ". " $0 }'
|
||||
printf "Pick a device: "
|
||||
read -r pick
|
||||
if [ -n "$pick" ] && [ "$pick" -eq "$pick" ]; then
|
||||
devname=$(printf '%s' "$names" | awk "NR==$pick")
|
||||
fi
|
||||
fi
|
||||
|
||||
selection=${NNN_SEL:-${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.selection}
|
||||
if [ -s "$selection" ]; then
|
||||
send < "$selection"
|
||||
[ -p "$NNN_PIPE" ] && printf "-" > "$NNN_PIPE" # clear selection
|
||||
elif [ -n "$1" ]; then
|
||||
printf "%s" "$1" | send
|
||||
else
|
||||
note "No selection and no hovered file"
|
||||
fi
|
||||
|
|
|
@ -9,7 +9,7 @@
|
|||
#
|
||||
# xfce4-terminal -e "${XDG_CONFIG_HOME:-$HOME/.config}/nnn/plugins/launch
|
||||
#
|
||||
# Requires: fzf/fzy
|
||||
# Dependencies: fzf
|
||||
#
|
||||
# Usage: launch [delay]
|
||||
# delay is in seconds, if omitted launch waits for 1 sec
|
||||
|
@ -24,10 +24,8 @@
|
|||
IFS=':'
|
||||
|
||||
get_selection() {
|
||||
if which fzf >/dev/null 2>&1; then
|
||||
if type fzf >/dev/null 2>&1; then
|
||||
{ IFS=':'; ls -H $PATH; } | sort | fzf
|
||||
elif which fzy >/dev/null 2>&1; then
|
||||
{ IFS=':'; ls -H $PATH; } | sort | fzy
|
||||
else
|
||||
exit 1
|
||||
fi
|
||||
|
@ -36,7 +34,7 @@ get_selection() {
|
|||
if selection=$( get_selection ); then
|
||||
setsid "$selection" 2>/dev/null 1>/dev/null &
|
||||
|
||||
if ! [ -z "$1" ]; then
|
||||
if [ -n "$1" ]; then
|
||||
sleep "$1"
|
||||
else
|
||||
sleep 1
|
||||
|
|
|
@ -1,13 +0,0 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: Show media information of a file in pager
|
||||
#
|
||||
# Requires: mediainfo
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Arun Prakash Jana
|
||||
|
||||
if ! [ -z "$1" ] && [ -f "$1" ]; then
|
||||
mediainfo "$1" | $PAGER
|
||||
# exiftool "$1" | $PAGER
|
||||
fi
|
|
@ -0,0 +1,23 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: Find and list files by mime type in smart context
|
||||
#
|
||||
# Dependencies:
|
||||
# - file
|
||||
# - mimetype (optional, PERL File MimeInfo)
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Arun Prakash Jana, Michel DHOOGE
|
||||
|
||||
# shellcheck disable=SC1090,SC1091
|
||||
. "$(dirname "$0")"/.nnn-plugin-helper
|
||||
|
||||
printf "mime (e.g., video/audio/image): "
|
||||
read -r mime
|
||||
|
||||
printf "%s" "+l" > "$NNN_PIPE"
|
||||
if type mimetype >/dev/null 2>&1; then
|
||||
find . | mimetype -f - | grep "$mime" | awk -F: '{printf "%s%c", $1, 0}' > "$NNN_PIPE"
|
||||
else
|
||||
find . | file -if- | grep "$mime" | awk -F: '{printf "%s%c", $1, 0}' > "$NNN_PIPE"
|
||||
fi
|
|
@ -1,7 +1,8 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: Fetches the lyrics of the track currently playing in MOC
|
||||
# Requires ddgr (https://github.com/jarun/ddgr)
|
||||
#
|
||||
# Dependencies: ddgr (https://github.com/jarun/ddgr)
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Arun Prakash Jana
|
||||
|
@ -26,14 +27,14 @@ fi
|
|||
ARTIST="$(echo "$out" | grep 'Artist:' | cut -d':' -f2 | sed 's/^[[:blank:]]*//;s/[[:blank:]]*$//')"
|
||||
TITLE="$(echo "$out" | grep 'SongTitle:' | cut -d':' -f2 | sed 's/^[[:blank:]]*//;s/[[:blank:]]*$//')"
|
||||
|
||||
if ! [ -z "$ARTIST" ] && ! [ -z "$TITLE" ]; then
|
||||
if [ -n "$ARTIST" ] && [ -n "$TITLE" ]; then
|
||||
ddgr -w azlyrics.com --ducky "$ARTIST" "$TITLE"
|
||||
else
|
||||
# Try by file name
|
||||
FILENAME="$(basename "$(echo "$out" | grep 'File:' | cut -d':' -f2)")"
|
||||
FILENAME="$(echo "${FILENAME%%.*}" | tr -d -)"
|
||||
|
||||
if ! [ -z "$FILENAME" ]; then
|
||||
if [ -n "$FILENAME" ]; then
|
||||
ddgr -w azlyrics.com --ducky "$FILENAME"
|
||||
fi
|
||||
fi
|
||||
|
|
|
@ -3,24 +3,23 @@
|
|||
# Description: Appends and optionally plays music in MOC
|
||||
#
|
||||
# Notes:
|
||||
# - if selection is available, plays it, else plays the current file or directory
|
||||
# - appends tracks and exits is MOC is running, else clears playlist and adds tracks
|
||||
# - to randomize the order of files appended to the playlist, set SHUFFLE=1
|
||||
# if you add a directory with many files when SHUFFLE=1 is set, it might take a very long time to finish!
|
||||
# - if selection is available, plays it, else plays the current file or directory
|
||||
# - appends tracks and exits is MOC is running, else clears playlist and adds tracks
|
||||
# - to let mocp shuffle tracks, set SHUFFLE=1
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Arun Prakash Jana, ath3
|
||||
# Authors: Arun Prakash Jana, ath3
|
||||
|
||||
IFS="$(printf '\n\r')"
|
||||
selection=${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.selection
|
||||
selection=${NNN_SEL:-${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.selection}
|
||||
cmd=$(pgrep -x mocp 2>/dev/null)
|
||||
ret=$cmd
|
||||
|
||||
SHUFFLE=0
|
||||
SHUFFLE="${SHUFFLE:-0}"
|
||||
|
||||
mocp_add ()
|
||||
{
|
||||
if [ $SHUFFLE = 1 ]; then
|
||||
if [ "$SHUFFLE" = 1 ]; then
|
||||
if [ "$resp" = "y" ]; then
|
||||
arr=$(tr '\0' '\n' < "$selection")
|
||||
elif [ -n "$1" ]; then
|
||||
|
@ -30,20 +29,14 @@ mocp_add ()
|
|||
for entry in $arr
|
||||
do
|
||||
if [ -d "$entry" ]; then
|
||||
arr2=$arr2$(find "$entry" -type f)
|
||||
else
|
||||
arr2=$arr2$(find "$entry" -type f \( ! -iname "*.m3u" ! -iname "*.pls" \))
|
||||
elif echo "$entry" | grep -qv '\.m3u$\|\.pls$' ; then
|
||||
arr2=$(printf "%s\n%s" "$entry" "$arr2")
|
||||
fi
|
||||
done
|
||||
|
||||
arr2=$(echo "$arr2" | awk 'BEGIN{srand();}{print rand()"\t"$0}' | sort -k1 -n | cut -f2-)
|
||||
for entry in $arr2
|
||||
do
|
||||
if [ -f "$entry" ] && echo "$entry" | grep -qv '\.m3u$\|\.pls$' ; then
|
||||
mocp -a "$entry"
|
||||
fi
|
||||
done
|
||||
|
||||
mocp -o shuffle
|
||||
echo "$arr2" | xargs -d "\n" mocp -a
|
||||
else
|
||||
if [ "$resp" = "y" ]; then
|
||||
xargs < "$selection" -0 mocp -a
|
||||
|
@ -57,7 +50,9 @@ if [ ! -s "$selection" ] && [ -z "$1" ]; then
|
|||
exit
|
||||
fi
|
||||
|
||||
if [ -s "$selection" ]; then
|
||||
if [ "$2" = "opener" ]; then
|
||||
:
|
||||
elif [ -s "$selection" ]; then
|
||||
printf "Work with selection? Enter 'y' to confirm: "
|
||||
read -r resp
|
||||
fi
|
||||
|
@ -87,3 +82,8 @@ mocp -p
|
|||
|
||||
# uncomment the line below to show mocp interface after appending
|
||||
# mocp
|
||||
|
||||
# Clear selection
|
||||
if [ "$resp" = "y" ] && [ -p "$NNN_PIPE" ]; then
|
||||
printf "-" > "$NNN_PIPE"
|
||||
fi
|
|
@ -0,0 +1,41 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: Extract audio from multimedia files and convert to mp3
|
||||
#
|
||||
# Dependencies: ffmpeg compiled with libmp3lame audio codec support
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Arun Prakash Jana
|
||||
|
||||
outdir=_mp3files
|
||||
|
||||
handle_multimedia() {
|
||||
mime="${1}"
|
||||
file="${2}"
|
||||
|
||||
case "${mime}" in
|
||||
audio/* | video/*)
|
||||
ffmpeg -i "${file}" -vn -codec:a libmp3lame -q:a 2 "${outdir}/${file%.*}.mp3"
|
||||
;;
|
||||
*)
|
||||
;;
|
||||
esac
|
||||
}
|
||||
|
||||
printf "Process 'a'll in directory or 'c'urrent? "
|
||||
read -r resp
|
||||
|
||||
if [ "$resp" = "a" ]; then
|
||||
if ! [ -e "${outdir}" ]; then
|
||||
mkdir "${outdir}"
|
||||
fi
|
||||
|
||||
for f in *; do
|
||||
if [ -f "${f}" ]; then
|
||||
mimestr="$( file --dereference --brief --mime-type -- "${f}" )"
|
||||
handle_multimedia "${mimestr}" "${f}"
|
||||
fi
|
||||
done
|
||||
elif [ "$resp" = "c" ] && [ -f "$1" ]; then
|
||||
ffmpeg -i "${1}" -vn -codec:a libmp3lame -q:a 2 "${1%.*}.mp3"
|
||||
fi
|
|
@ -0,0 +1,76 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: Toggle mount of MTP device (eg. Android device)
|
||||
# 'l' to list mountable devices
|
||||
# 'n' integer associated to device to mount
|
||||
# 'q'/'Return' exit
|
||||
#
|
||||
# Dependencies: gvfs-mtp
|
||||
#
|
||||
# Notes: The MTP device should be mounted at /run/user/$UID/gvfs.
|
||||
# Put /run/user/$UID/gvfs to bookmark entries (NNN_BMS) for faster access.
|
||||
# Make sure the device is unlocked when mounting.
|
||||
#
|
||||
# When doing copy-paste into MTP device, you will get an error like this:
|
||||
# cp: preserving times for './gambar1.png': Operation not supported
|
||||
# That just means the file is copied but timestamp won't be preserved.
|
||||
# It's like doing `cp -p localfile.txt file-to-SMB.txt`.
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Benawi Adha
|
||||
|
||||
prompt="Device number ('l' to list): "
|
||||
|
||||
IFS='
|
||||
'
|
||||
|
||||
lsmtp () {
|
||||
devs=$(gio mount -li | grep -e 'activation_root' | sed 's/\s*activation_root=//g')
|
||||
c=1
|
||||
printf "Devices list:\n"
|
||||
for i in $devs; do
|
||||
printf "%s %s\\n" "$c" "$i"
|
||||
c=$(( c + 1 ))
|
||||
done
|
||||
echo
|
||||
}
|
||||
|
||||
lsmtp
|
||||
printf "%s" "$prompt"
|
||||
read -r input
|
||||
|
||||
while [ -n "$input" ]
|
||||
do
|
||||
if [ "$input" = "l" ]; then
|
||||
lsmtp
|
||||
elif [ "$input" = "q" ] || [ "$input" -eq 0 ]; then
|
||||
exit
|
||||
elif [ "$input" -le "$(printf '%s\n' "${devs}" | grep -c '^')" ]; then
|
||||
# dev=$(printf "%s\n" "$devs" | cut -d$'\n' -f${input})
|
||||
c=1
|
||||
for i in $devs; do
|
||||
dev=$i
|
||||
if [ "$input" -eq $c ]; then
|
||||
break
|
||||
fi
|
||||
c=$(( c + 1 ))
|
||||
done
|
||||
|
||||
if (gio mount -l | grep '^Mount([1-9]).*'"$dev" ) 1>/dev/null; then
|
||||
if gio mount -u "${dev}"; then
|
||||
printf "%s unmounted\n" "$dev"
|
||||
fi
|
||||
else
|
||||
if gio mount "${dev}"; then
|
||||
printf "%s mounted to /run/user/\$UID/gvfs\n" "$dev"
|
||||
fi
|
||||
fi
|
||||
echo
|
||||
else
|
||||
printf "Invalid input\n"
|
||||
fi
|
||||
|
||||
printf "%s" "$prompt"
|
||||
read -r input
|
||||
done
|
||||
|
|
@ -0,0 +1,75 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: Backup nnn configuration
|
||||
# - config dir content
|
||||
# - environment config
|
||||
# - shell functions and aliases
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Léo Villeveygoux
|
||||
|
||||
nnn_aliases="n nnn"
|
||||
|
||||
outdir="nnn-$(whoami)@$(hostname)"
|
||||
|
||||
outfile="${outdir}.tar.bz2"
|
||||
|
||||
shellname="$(basename "$SHELL")"
|
||||
|
||||
conffile="config.txt"
|
||||
|
||||
configdir="${XDG_CONFIG_HOME:-$HOME/.config}/nnn"
|
||||
|
||||
workdir="$PWD"
|
||||
|
||||
tempdir="$(mktemp -d)"
|
||||
|
||||
mkdir "$tempdir/$outdir"
|
||||
|
||||
if [ ! -d "$tempdir" ]; then
|
||||
echo "Can't create work directory." >&2
|
||||
exit 1
|
||||
fi
|
||||
|
||||
cd "$tempdir/$outdir" || exit 1
|
||||
|
||||
# Backing up config dir content
|
||||
cp -r -- "$configdir" . || exit 1
|
||||
|
||||
# Environment config
|
||||
env | sed "s/'/'\\\\''/" |\
|
||||
awk '/^NNN_/{print "export '\''"$0"'\''"}' > "$conffile"
|
||||
|
||||
# Shell functions/aliases
|
||||
case "$shellname" in
|
||||
bash)
|
||||
for name in $nnn_aliases ; do
|
||||
if [ "$(bash -ic "type -t $name")" = "function" ] ; then
|
||||
bash -ic "type $name" | tail -n+2 >> "$conffile"
|
||||
elif bash -ic "alias $name" >/dev/null 2>&1 ; then
|
||||
bash -ic "alias $name" >> "$conffile"
|
||||
fi
|
||||
done
|
||||
;;
|
||||
zsh)
|
||||
for name in $nnn_aliases ; do
|
||||
if zsh -ic "functions $name" ; then
|
||||
zsh -ic "functions $name" >> "$conffile"
|
||||
elif zsh -ic "alias $name" ; then
|
||||
echo alias "$(zsh -ic "alias $name")" >> "$conffile"
|
||||
fi
|
||||
done
|
||||
;;
|
||||
|
||||
*)
|
||||
echo "Unknown shell, skipping alias/function checking." >&2
|
||||
;;
|
||||
esac
|
||||
|
||||
cd .. || exit 1
|
||||
|
||||
printf "Saving as '%s' ... " "$workdir/$outfile"
|
||||
|
||||
tar caf "$workdir/$outfile" "$outdir" && echo "Done" || echo "Failed"
|
||||
|
||||
cd "$workdir" && rm -rf -- "$tempdir"
|
|
@ -4,19 +4,21 @@
|
|||
# If the device is not mounted, it will be mounted.
|
||||
# If the device is mounted, it will be unmounted and powered down.
|
||||
#
|
||||
# Runs `lsblk` if 'l' is entered, exits on 'Return`.
|
||||
# Dependencies: lsblk, pmount (optional), udisks2
|
||||
#
|
||||
# Note:
|
||||
# - The script uses Linux-specific lsblk to list block devices. Alternatives:
|
||||
# Usage: Runs `lsblk` on 'l', exits on 'Return`.
|
||||
#
|
||||
# Notes:
|
||||
# - The script uses Linux-specific lsblk to list block devices. Alternatives:
|
||||
# macOS: "diskutil list"
|
||||
# BSD: "geom disk list"
|
||||
# - The script uses udisksctl (from udisks2) to pwoer down devices. This is also Linux-specific.
|
||||
# Users on non-Linux platforms can comment it and use an alterntive to power-down disks.
|
||||
# - The script uses udisksctl (from udisks2) to power down devices. This is also Linux-specific.
|
||||
# Users on non-Linux platforms can comment it and use an alternative to power-down disks.
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Arun Prakash Jana
|
||||
|
||||
prompt="device name ['l' lists]: "
|
||||
prompt="device name [e.g. sdXn] ('l'ist, 'q'uit): "
|
||||
|
||||
lsblk
|
||||
|
||||
|
@ -24,26 +26,59 @@ printf "\nEnsure you aren't still in the mounted device.\n"
|
|||
printf "%s" "$prompt"
|
||||
read -r dev
|
||||
|
||||
while ! [ -z "$dev" ]
|
||||
do
|
||||
while [ -n "$dev" ]; do
|
||||
if [ "$dev" = "l" ]; then
|
||||
lsblk
|
||||
elif [ "$dev" = "q" ]; then
|
||||
exit
|
||||
else
|
||||
if grep -qs "$dev " /proc/mounts; then
|
||||
sync
|
||||
if pumount "$dev"
|
||||
then
|
||||
echo "$dev" unmounted.
|
||||
if udisksctl power-off -b /dev/"$dev"
|
||||
then
|
||||
echo "$dev" ejected.
|
||||
# LUKS volumes mounted with udisksctl appear differently than with pmount
|
||||
if grep -qs "$dev " /proc/mounts || [ -n "$(lsblk -n "/dev/$dev" -o MOUNTPOINT)" ]; then
|
||||
sync "$(lsblk -n "/dev/$dev" -o MOUNTPOINT | sed "/^$/d")"
|
||||
if type pumount >/dev/null 2>&1; then
|
||||
pumount "/dev/$dev"
|
||||
exit_code="$?"
|
||||
else
|
||||
# Unlike pmount, udisksctl does not transparently handle LUKS volumes
|
||||
# We need to manually get the unlocked device, unmount it, and then lock the volume
|
||||
if lsblk -n "/dev/$dev" -o FSTYPE | grep "crypto_LUKS" >/dev/null; then
|
||||
dev_map="$(udisksctl info -b /dev/"$dev" | grep "CleartextDevice" | grep -o "dm_2d[[:digit:]]*" | sed "s/_2d/-/")"
|
||||
udisksctl unmount -b "/dev/$dev_map" --no-user-interaction >/dev/null
|
||||
exit_code="$?"
|
||||
udisksctl lock -b "/dev/$dev" --no-user-interaction >/dev/null
|
||||
else
|
||||
udisksctl unmount -b "/dev/$dev" --no-user-interaction >/dev/null
|
||||
exit_code="$?"
|
||||
fi
|
||||
fi
|
||||
if [ $exit_code -eq 0 ]; then
|
||||
echo "/dev/$dev unmounted."
|
||||
if udisksctl power-off -b "/dev/$dev" --no-user-interaction; then
|
||||
echo "/dev/$dev ejected."
|
||||
fi
|
||||
fi
|
||||
elif [ -b "/dev/$dev" ]; then
|
||||
if type pmount >/dev/null 2>&1; then
|
||||
pmount "/dev/$dev"
|
||||
exit_code="$?"
|
||||
else
|
||||
# Unlike pmount, udisksctl does not transparently handle LUKS volumes
|
||||
# We need to manually get the unlocked device and mount that instead of the volume itself
|
||||
if [ "$(lsblk "/dev/$dev" -n -o FSTYPE)" = "crypto_LUKS" ]; then
|
||||
dev_map=$(udisksctl unlock -b "/dev/$dev" --no-user-interaction | grep -o "dm-[[:digit:]]*")
|
||||
udisksctl mount -b "/dev/$dev_map" --no-user-interaction >/dev/null
|
||||
exit_code="$?"
|
||||
else
|
||||
udisksctl mount -b "/dev/$dev" --no-user-interaction >/dev/null
|
||||
exit_code="$?"
|
||||
fi
|
||||
fi
|
||||
if [ $exit_code -eq 0 ]; then
|
||||
sleep 1
|
||||
echo "/dev/$dev mounted to $(lsblk -n "/dev/$dev" -o MOUNTPOINT | sed "/^$/d")."
|
||||
fi
|
||||
else
|
||||
pmount "$dev"
|
||||
echo "$dev" mounted to "$(lsblk -n /dev/"$dev" | rev | cut -d' ' -f1 | rev)".
|
||||
echo "/dev/$dev does not exist or is not a block device."
|
||||
fi
|
||||
fi
|
||||
|
||||
|
|
371
plugins/nuke
371
plugins/nuke
|
@ -1,6 +1,5 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# #############################################################################
|
||||
# Description: Sample script to play files in apps by file type or mime
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
|
@ -13,8 +12,8 @@
|
|||
# # export NNN_OPENER=nuke
|
||||
# 2. Run nnn with the program option to indicate a CLI opener
|
||||
# nnn -c
|
||||
# # The -c program option overrides config `NNN_USE_EDITOR`
|
||||
# 3. nuke can use nnn plugins (e.g. mocplay is used for audio), $PATH is updated.
|
||||
# # The -c program option overrides option -e
|
||||
# 3. nuke can use nnn plugins (e.g. mocq is used for audio), $PATH is updated.
|
||||
#
|
||||
# Details:
|
||||
# Inspired by ranger's scope.sh, modified for usage with nnn.
|
||||
|
@ -22,9 +21,10 @@
|
|||
# Guards against accidentally opening mime types like executables, shared libs etc.
|
||||
#
|
||||
# Tries to play 'file' (1st argument) in the following order:
|
||||
# i. by extension
|
||||
# ii. by mime (image, video, audio, pdf)
|
||||
# iii. by mime (other file types)
|
||||
# 1. by extension
|
||||
# 2. by mime (image, video, audio, pdf)
|
||||
# 3. by mime (other file types)
|
||||
# 4. by mime (prompt and run executables)
|
||||
#
|
||||
# Modification tips:
|
||||
# 1. Invokes CLI utilities by default. Set GUI to 1 to enable GUI apps.
|
||||
|
@ -32,38 +32,41 @@
|
|||
# 3. Start GUI apps in bg to unblock. Redirect stdout and strerr if required.
|
||||
# 4. Some CLI utilities are piped to the $PAGER, to wait and quit uniformly.
|
||||
# 5. If the output cannot be paged use "read -r _" to wait for user input.
|
||||
# 6. On a DE, try 'xdg-open' in handle_fallback() as last resort.
|
||||
# 6. On a DE, try 'xdg-open' or 'open' in handle_fallback() as last resort.
|
||||
#
|
||||
# Feel free to change the utilities to your favourites and add more mimes.
|
||||
#
|
||||
# Defaults:
|
||||
# By extension (only the enbaled ones):
|
||||
# By extension (only the enabled ones):
|
||||
# most archives: list with atool, bsdtar
|
||||
# rar: list with unrar
|
||||
# 7-zip: list with 7z
|
||||
# pdf: zathura (GUI), pdftotext, mutool, exiftool
|
||||
# audio: mocplay (nnn plugin using MOC), mpv, mediainfo, exiftool
|
||||
# audio: mocq (nnn plugin using MOC), mpv, media_client (Haiku), mediainfo, exiftool
|
||||
# avi|mkv|mp4: smplayer, mpv (GUI), ffmpegthumbnailer, mediainfo, exiftool
|
||||
# log: vi
|
||||
# torrent: rtorrent, transmission-show
|
||||
# odt|ods|odp|sxw: odt2txt
|
||||
# md: glow (https://github.com/charmbracelet/glow), lowdown (https://kristaps.bsd.lv/lowdown)
|
||||
# htm|html|xhtml: w3m, lynx, elinks
|
||||
# json: jq, python (json.tool module)
|
||||
# Multimedia by mime:
|
||||
# image/*: sxiv (GUI), viu, img2txt, exiftool
|
||||
# image/*: imv/sxiv/nsxiv (GUI), viu (https://github.com/atanunq/viu), img2txt, exiftool
|
||||
# video/*: smplayer, mpv (GUI), ffmpegthumbnailer, mediainfo, exiftool
|
||||
# audio/*: mocplay (nnn plugin using MOC), mpv, mediainfo, exiftool
|
||||
# audio/*: mocq (nnn plugin using MOC), mpv, media_client (Haiku), mediainfo, exiftool
|
||||
# application/pdf: zathura (GUI), pdftotext, mutool, exiftool
|
||||
# Other mimes:
|
||||
# text/troff: man -l
|
||||
# text/* | */xml: vi
|
||||
# image/vnd.djvu): djvutxt, exiftool
|
||||
#
|
||||
# ToDo:
|
||||
# TODO:
|
||||
# 1. Adapt, test and enable all mimes
|
||||
# 2. Clean-up unnecessary the exit codes
|
||||
# #############################################################################
|
||||
# 2. Clean-up the unnecessary exit codes
|
||||
|
||||
# set to 1 to enable GUI apps
|
||||
GUI=0
|
||||
# set to 1 to enable GUI apps and/or BIN execution
|
||||
GUI="${GUI:-0}"
|
||||
BIN="${BIN:-0}"
|
||||
|
||||
set -euf -o noclobber -o noglob -o nounset
|
||||
IFS="$(printf '%b_' '\n')"; IFS="${IFS%_}" # protect trailing \n
|
||||
|
@ -73,26 +76,80 @@ IMAGE_CACHE_PATH="$(dirname "$1")"/.thumbs
|
|||
|
||||
FPATH="$1"
|
||||
FNAME=$(basename "$1")
|
||||
EDITOR="${VISUAL:-${EDITOR:-vi}}"
|
||||
PAGER="${PAGER:-less -R}"
|
||||
ext="${FNAME##*.}"
|
||||
if ! [ -z "$ext" ]; then
|
||||
if [ -n "$ext" ]; then
|
||||
ext="$(printf "%s" "${ext}" | tr '[:upper:]' '[:lower:]')"
|
||||
fi
|
||||
|
||||
is_mac() {
|
||||
uname | grep -q "Darwin"
|
||||
}
|
||||
|
||||
handle_pdf() {
|
||||
if [ $GUI -ne 0 ] && which zathura >/dev/null 2>&1; then
|
||||
zathura "${FPATH}" >/dev/null 2>&1 &
|
||||
exit 0
|
||||
elif which pdftotext >/dev/null 2>&1; then
|
||||
if [ "$GUI" -ne 0 ]; then
|
||||
if is_mac; then
|
||||
nohup open "${FPATH}" >/dev/null 2>&1 &
|
||||
elif type zathura >/dev/null 2>&1; then
|
||||
nohup zathura "${FPATH}" >/dev/null 2>&1 &
|
||||
else
|
||||
return
|
||||
fi
|
||||
elif type pdftotext >/dev/null 2>&1; then
|
||||
## Preview as text conversion
|
||||
pdftotext -l 10 -nopgbrk -q -- "${FPATH}" - | less -R
|
||||
exit 0
|
||||
elif which mutool >/dev/null 2>&1; then
|
||||
mutool draw -F txt -i -- "${FPATH}" 1-10
|
||||
exit 0
|
||||
elif which exiftool >/dev/null 2>&1; then
|
||||
exiftool "${FPATH}" | less -R
|
||||
exit 0
|
||||
pdftotext -l 10 -nopgbrk -q -- "${FPATH}" - | eval "$PAGER"
|
||||
elif type mutool >/dev/null 2>&1; then
|
||||
mutool draw -F txt -i -- "${FPATH}" 1-10 | eval "$PAGER"
|
||||
elif type exiftool >/dev/null 2>&1; then
|
||||
exiftool "${FPATH}" | eval "$PAGER"
|
||||
else
|
||||
return
|
||||
fi
|
||||
exit 0
|
||||
}
|
||||
|
||||
handle_audio() {
|
||||
if type mocp >/dev/null 2>&1 && type mocq >/dev/null 2>&1; then
|
||||
mocq "${FPATH}" "opener" >/dev/null 2>&1
|
||||
elif type mpv >/dev/null 2>&1; then
|
||||
mpv "${FPATH}" >/dev/null 2>&1 &
|
||||
elif type media_client >/dev/null 2>&1; then
|
||||
media_client play "${FPATH}" >/dev/null 2>&1 &
|
||||
elif type mediainfo >/dev/null 2>&1; then
|
||||
mediainfo "${FPATH}" | eval "$PAGER"
|
||||
elif type exiftool >/dev/null 2>&1; then
|
||||
exiftool "${FPATH}"| eval "$PAGER"
|
||||
else
|
||||
return
|
||||
fi
|
||||
exit 0
|
||||
}
|
||||
|
||||
handle_video() {
|
||||
if [ "$GUI" -ne 0 ]; then
|
||||
if is_mac; then
|
||||
nohup open "${FPATH}" >/dev/null 2>&1 &
|
||||
elif type smplayer >/dev/null 2>&1; then
|
||||
nohup smplayer "${FPATH}" >/dev/null 2>&1 &
|
||||
elif type mpv >/dev/null 2>&1; then
|
||||
nohup mpv "${FPATH}" >/dev/null 2>&1 &
|
||||
else
|
||||
return
|
||||
fi
|
||||
elif type ffmpegthumbnailer >/dev/null 2>&1; then
|
||||
# Thumbnail
|
||||
[ -d "${IMAGE_CACHE_PATH}" ] || mkdir "${IMAGE_CACHE_PATH}"
|
||||
ffmpegthumbnailer -i "${FPATH}" -o "${IMAGE_CACHE_PATH}/${FNAME}.jpg" -s 0
|
||||
viu -n "${IMAGE_CACHE_PATH}/${FNAME}.jpg" | eval "$PAGER"
|
||||
elif type mediainfo >/dev/null 2>&1; then
|
||||
mediainfo "${FPATH}" | eval "$PAGER"
|
||||
elif type exiftool >/dev/null 2>&1; then
|
||||
exiftool "${FPATH}"| eval "$PAGER"
|
||||
else
|
||||
return
|
||||
fi
|
||||
exit 0
|
||||
}
|
||||
|
||||
# handle this extension and exit
|
||||
|
@ -101,24 +158,24 @@ handle_extension() {
|
|||
## Archive
|
||||
a|ace|alz|arc|arj|bz|bz2|cab|cpio|deb|gz|jar|lha|lz|lzh|lzma|lzo|\
|
||||
rpm|rz|t7z|tar|tbz|tbz2|tgz|tlz|txz|tZ|tzo|war|xpi|xz|Z|zip)
|
||||
if which atool >/dev/null 2>&1; then
|
||||
atool --list -- "${FPATH}" | less -R
|
||||
if type atool >/dev/null 2>&1; then
|
||||
atool --list -- "${FPATH}" | eval "$PAGER"
|
||||
exit 0
|
||||
elif which bsdtar >/dev/null 2>&1; then
|
||||
bsdtar --list --file "${FPATH}" | less -R
|
||||
elif type bsdtar >/dev/null 2>&1; then
|
||||
bsdtar --list --file "${FPATH}" | eval "$PAGER"
|
||||
exit 0
|
||||
fi
|
||||
exit 1;;
|
||||
rar)
|
||||
if which unrar >/dev/null 2>&1; then
|
||||
if type unrar >/dev/null 2>&1; then
|
||||
## Avoid password prompt by providing empty password
|
||||
unrar lt -p- -- "${FPATH}" | less -R
|
||||
unrar lt -p- -- "${FPATH}" | eval "$PAGER"
|
||||
fi
|
||||
exit 1;;
|
||||
7z)
|
||||
if which 7z >/dev/null 2>&1; then
|
||||
if type 7z >/dev/null 2>&1; then
|
||||
## Avoid password prompt by providing empty password
|
||||
7z l -p -- "${FPATH}" | less -R
|
||||
7z l -p -- "${FPATH}" | eval "$PAGER"
|
||||
exit 0
|
||||
fi
|
||||
exit 1;;
|
||||
|
@ -130,27 +187,25 @@ handle_extension() {
|
|||
|
||||
## Audio
|
||||
aac|flac|m4a|mid|midi|mpa|mp2|mp3|ogg|wav|wma)
|
||||
if which mocp >/dev/null 2>&1; then
|
||||
mocplay "${FPATH}" >/dev/null 2>&1
|
||||
exit 0
|
||||
elif which mpv >/dev/null 2>&1; then
|
||||
mpv "${FPATH}" >/dev/null 2>&1 &
|
||||
exit 0
|
||||
elif which mediainfo >/dev/null 2>&1; then
|
||||
mediainfo "${FPATH}" | less -R
|
||||
exit 0
|
||||
elif which exiftool >/dev/null 2>&1; then
|
||||
exiftool "${FPATH}"| less -R
|
||||
exit 0
|
||||
fi
|
||||
handle_audio
|
||||
exit 1;;
|
||||
|
||||
## Video
|
||||
avi|mkv|mp4)
|
||||
handle_video
|
||||
exit 1;;
|
||||
|
||||
## Log files
|
||||
log)
|
||||
"$EDITOR" "${FPATH}"
|
||||
exit 0;;
|
||||
|
||||
## BitTorrent
|
||||
torrent)
|
||||
if which rtorrent >/dev/null 2>&1; then
|
||||
if type rtorrent >/dev/null 2>&1; then
|
||||
rtorrent "${FPATH}"
|
||||
exit 0
|
||||
elif which transmission-show >/dev/null 2>&1; then
|
||||
elif type transmission-show >/dev/null 2>&1; then
|
||||
transmission-show -- "${FPATH}"
|
||||
exit 0
|
||||
fi
|
||||
|
@ -158,40 +213,85 @@ handle_extension() {
|
|||
|
||||
## OpenDocument
|
||||
odt|ods|odp|sxw)
|
||||
if which odt2txt >/dev/null 2>&1; then
|
||||
if type odt2txt >/dev/null 2>&1; then
|
||||
## Preview as text conversion
|
||||
odt2txt "${FPATH}" | less -R
|
||||
odt2txt "${FPATH}" | eval "$PAGER"
|
||||
exit 0
|
||||
fi
|
||||
exit 1;;
|
||||
|
||||
## HTML
|
||||
htm|html|xhtml)
|
||||
## Preview as text conversion
|
||||
if which w3m >/dev/null 2>&1; then
|
||||
w3m -dump "${FPATH}" | less -R
|
||||
## Markdown
|
||||
md)
|
||||
if type glow >/dev/null 2>&1; then
|
||||
glow -sdark "${FPATH}" | eval "$PAGER"
|
||||
exit 0
|
||||
elif which lynx >/dev/null 2>&1; then
|
||||
lynx -dump -- "${FPATH}" | less -R
|
||||
exit 0
|
||||
elif which elinks >/dev/null 2>&1; then
|
||||
elinks -dump "${FPATH}" | less -R
|
||||
elif type lowdown >/dev/null 2>&1; then
|
||||
lowdown -Tterm "${FPATH}" | eval "$PAGER"
|
||||
exit 0
|
||||
fi
|
||||
;;
|
||||
|
||||
## HTML
|
||||
htm|html|xhtml)
|
||||
## Preview as text conversion
|
||||
if type w3m >/dev/null 2>&1; then
|
||||
w3m -dump "${FPATH}" | eval "$PAGER"
|
||||
exit 0
|
||||
elif type lynx >/dev/null 2>&1; then
|
||||
lynx -dump -- "${FPATH}" | eval "$PAGER"
|
||||
exit 0
|
||||
elif type elinks >/dev/null 2>&1; then
|
||||
elinks -dump "${FPATH}" | eval "$PAGER"
|
||||
exit 0
|
||||
fi
|
||||
;;
|
||||
|
||||
## JSON
|
||||
json)
|
||||
if which jq >/dev/null 2>&1; then
|
||||
jq --color-output . "${FPATH}" | less -R
|
||||
if type jq >/dev/null 2>&1; then
|
||||
jq --color-output . "${FPATH}" | eval "$PAGER"
|
||||
exit 0
|
||||
elif which python >/dev/null 2>&1; then
|
||||
python -m json.tool -- "${FPATH}" | less -R
|
||||
elif type python >/dev/null 2>&1; then
|
||||
python -m json.tool -- "${FPATH}" | eval "$PAGER"
|
||||
exit 0
|
||||
fi
|
||||
;;
|
||||
esac
|
||||
}
|
||||
|
||||
# sets the variable abs_target, this should be faster than calling printf
|
||||
abspath() {
|
||||
case "$1" in
|
||||
/*) abs_target="$1";;
|
||||
*) abs_target="$PWD/$1";;
|
||||
esac
|
||||
}
|
||||
|
||||
# storing the result to a tmp file is faster than calling listimages twice
|
||||
listimages() {
|
||||
find -L "///${1%/*}" -maxdepth 1 -type f -print0 |
|
||||
grep -izZE '\.(jpe?g|png|gif|webp|tiff|bmp|ico|svg)$' |
|
||||
sort -zV | tee "$tmp"
|
||||
}
|
||||
|
||||
load_dir() {
|
||||
abspath "$2"
|
||||
tmp="${TMPDIR:-/tmp}/nuke_$$"
|
||||
trap 'rm -f -- "$tmp"' EXIT
|
||||
count="$(listimages "$abs_target" | grep -a -m 1 -ZznF "$abs_target" | cut -d: -f1)"
|
||||
|
||||
if [ -n "$count" ]; then
|
||||
if [ "$GUI" -ne 0 ]; then
|
||||
xargs -0 nohup "$1" -n "$count" -- < "$tmp"
|
||||
else
|
||||
xargs -0 "$1" -n "$count" -- < "$tmp"
|
||||
fi
|
||||
else
|
||||
shift
|
||||
"$1" -- "$@" # fallback
|
||||
fi
|
||||
}
|
||||
|
||||
handle_multimedia() {
|
||||
## Size of the preview if there are multiple options or it has to be
|
||||
## rendered from vector graphics. If the conversion program allows
|
||||
|
@ -214,17 +314,31 @@ handle_multimedia() {
|
|||
|
||||
## Image
|
||||
image/*)
|
||||
if [ $GUI -ne 0 ] && which sxiv >/dev/null 2>&1; then
|
||||
sxiv -q "${FPATH}" &
|
||||
if [ "$GUI" -ne 0 ]; then
|
||||
if is_mac; then
|
||||
nohup open "${FPATH}" >/dev/null 2>&1 &
|
||||
exit 0
|
||||
elif type imv >/dev/null 2>&1; then
|
||||
load_dir imv "${FPATH}" >/dev/null 2>&1 &
|
||||
exit 0
|
||||
elif type imvr >/dev/null 2>&1; then
|
||||
load_dir imvr "${FPATH}" >/dev/null 2>&1 &
|
||||
exit 0
|
||||
elif type sxiv >/dev/null 2>&1; then
|
||||
load_dir sxiv "${FPATH}" >/dev/null 2>&1 &
|
||||
exit 0
|
||||
elif type nsxiv >/dev/null 2>&1; then
|
||||
load_dir nsxiv "${FPATH}" >/dev/null 2>&1 &
|
||||
exit 0
|
||||
fi
|
||||
elif type viu >/dev/null 2>&1; then
|
||||
viu -n "${FPATH}" | eval "$PAGER"
|
||||
exit 0
|
||||
elif which viu >/dev/null 2>&1; then
|
||||
viu -n "${FPATH}" | less -R
|
||||
elif type img2txt >/dev/null 2>&1; then
|
||||
img2txt --gamma=0.6 -- "${FPATH}" | eval "$PAGER"
|
||||
exit 0
|
||||
elif which img2txt >/dev/null 2>&1; then
|
||||
img2txt --gamma=0.6 -- "${FPATH}" | less -R
|
||||
exit 0
|
||||
elif which exiftool >/dev/null 2>&1; then
|
||||
exiftool "${FPATH}" | less -R
|
||||
elif type exiftool >/dev/null 2>&1; then
|
||||
exiftool "${FPATH}" | eval "$PAGER"
|
||||
exit 0
|
||||
fi
|
||||
# local orientation
|
||||
|
@ -236,55 +350,25 @@ handle_multimedia() {
|
|||
# convert -- "${FPATH}" -auto-orient "${IMAGE_CACHE_PATH}" && exit 6
|
||||
# fi
|
||||
|
||||
## `w3mimgdisplay` will be called for all images (unless overriden
|
||||
## `w3mimgdisplay` will be called for all images (unless overridden
|
||||
## as above), but might fail for unsupported types.
|
||||
exit 7;;
|
||||
|
||||
## Video
|
||||
video/*)
|
||||
if [ $GUI -ne 0 ] && which smplayer >/dev/null 2>&1; then
|
||||
smplayer "${FPATH}" >/dev/null 2>&1 &
|
||||
exit 0
|
||||
elif [ $GUI -ne 0 ] && which mpv >/dev/null 2>&1; then
|
||||
mpv "${FPATH}" >/dev/null 2>&1 &
|
||||
exit 0
|
||||
elif which ffmpegthumbnailer >/dev/null 2>&1; then
|
||||
# Thumbnail
|
||||
[ -d "${IMAGE_CACHE_PATH}" ] || mkdir "${IMAGE_CACHE_PATH}"
|
||||
ffmpegthumbnailer -i "${FPATH}" -o "${IMAGE_CACHE_PATH}/${FNAME}.jpg" -s 0
|
||||
viu -n "${IMAGE_CACHE_PATH}/${FNAME}.jpg" | less -R
|
||||
exit 0
|
||||
elif which mediainfo >/dev/null 2>&1; then
|
||||
mediainfo "${FPATH}" | less -R
|
||||
exit 0
|
||||
elif which exiftool >/dev/null 2>&1; then
|
||||
exiftool "${FPATH}"| less -R
|
||||
exit 0
|
||||
fi
|
||||
exit 1;;
|
||||
|
||||
## Audio
|
||||
audio/*)
|
||||
if which mocp >/dev/null 2>&1; then
|
||||
mocplay "${FPATH}" >/dev/null 2>&1
|
||||
exit 0
|
||||
elif which mpv >/dev/null 2>&1; then
|
||||
mpv "${FPATH}" >/dev/null 2>&1 &
|
||||
exit 0
|
||||
elif which mediainfo >/dev/null 2>&1; then
|
||||
mediainfo "${FPATH}" | less -R
|
||||
exit 0
|
||||
elif which exiftool >/dev/null 2>&1; then
|
||||
exiftool "${FPATH}"| less -R
|
||||
exit 0
|
||||
fi
|
||||
exit 1;;
|
||||
|
||||
## PDF
|
||||
application/pdf)
|
||||
handle_pdf
|
||||
exit 1;;
|
||||
|
||||
## Audio
|
||||
audio/*)
|
||||
handle_audio
|
||||
exit 1;;
|
||||
|
||||
## Video
|
||||
video/*)
|
||||
handle_video
|
||||
exit 1;;
|
||||
|
||||
# pdftoppm -f 1 -l 1 \
|
||||
# -scale-to-x "${DEFAULT_SIZE%x*}" \
|
||||
# -scale-to-y -1 \
|
||||
|
@ -318,7 +402,7 @@ handle_multimedia() {
|
|||
# "${FPATH}";
|
||||
# then
|
||||
# convert -- "${preview_png}" "${IMAGE_CACHE_PATH}" \
|
||||
# && rm "${preview_png}" \
|
||||
# && rm -- "${preview_png}" \
|
||||
# && exit 6
|
||||
# else
|
||||
# exit 1
|
||||
|
@ -374,8 +458,8 @@ handle_mime() {
|
|||
|
||||
## Text
|
||||
text/* | */xml)
|
||||
vi "${FPATH}"
|
||||
exit 1;;
|
||||
"$EDITOR" "${FPATH}"
|
||||
exit 0;;
|
||||
## Syntax highlight
|
||||
# if [[ "$( stat --printf='%s' -- "${FPATH}" )" -gt "${HIGHLIGHT_SIZE_MAX}" ]]; then
|
||||
# exit 2
|
||||
|
@ -396,12 +480,12 @@ handle_mime() {
|
|||
|
||||
## DjVu
|
||||
image/vnd.djvu)
|
||||
if which djvutxt >/dev/null 2>&1; then
|
||||
if type djvutxt >/dev/null 2>&1; then
|
||||
## Preview as text conversion (requires djvulibre)
|
||||
djvutxt "${FPATH}" | less -R
|
||||
djvutxt "${FPATH}" | eval "$PAGER"
|
||||
exit 0
|
||||
elif which exiftool >/dev/null 2>&1; then
|
||||
exiftool "${FPATH}" | less -R
|
||||
elif type exiftool >/dev/null 2>&1; then
|
||||
exiftool "${FPATH}" | eval "$PAGER"
|
||||
exit 0
|
||||
fi
|
||||
exit 1;;
|
||||
|
@ -409,9 +493,14 @@ handle_mime() {
|
|||
}
|
||||
|
||||
handle_fallback() {
|
||||
if [ $GUI -ne 0 ]; then
|
||||
xdg-open "${FPATH}" >/dev/null 2>&1 &
|
||||
exit 0
|
||||
if [ "$GUI" -ne 0 ]; then
|
||||
if type xdg-open >/dev/null 2>&1; then
|
||||
nohup xdg-open "${FPATH}" >/dev/null 2>&1 &
|
||||
exit 0
|
||||
elif type open >/dev/null 2>&1; then
|
||||
nohup open "${FPATH}" >/dev/null 2>&1 &
|
||||
exit 0
|
||||
fi
|
||||
fi
|
||||
|
||||
echo '----- File details -----' && file --dereference --brief -- "${FPATH}"
|
||||
|
@ -431,14 +520,36 @@ handle_blocked() {
|
|||
|
||||
application/x-shellscript)
|
||||
exit 0;;
|
||||
|
||||
application/octet-stream)
|
||||
exit 0;;
|
||||
esac
|
||||
}
|
||||
|
||||
MIMETYPE="$( file --dereference --brief --mime-type -- "${FPATH}" )"
|
||||
handle_blocked "${MIMETYPE}"
|
||||
handle_bin() {
|
||||
case "${MIMETYPE}" in
|
||||
application/x-executable|application/x-shellscript)
|
||||
clear
|
||||
echo '-------- Executable File --------' && file --dereference --brief -- "${FPATH}"
|
||||
printf "Run executable (y/N/'a'rgs)? "
|
||||
read -r answer
|
||||
case "$answer" in
|
||||
[Yy]* ) exec "${FPATH}";;
|
||||
[Aa]* )
|
||||
printf "args: "
|
||||
read -r args
|
||||
exec "${FPATH}" "$args";;
|
||||
[Nn]* ) exit;;
|
||||
esac
|
||||
esac
|
||||
}
|
||||
|
||||
MIMETYPE="$( file -bL --mime-type -- "${FPATH}" )"
|
||||
handle_extension
|
||||
handle_multimedia "${MIMETYPE}"
|
||||
handle_mime "${MIMETYPE}"
|
||||
[ "$BIN" -ne 0 ] && [ -x "${FPATH}" ] && handle_bin
|
||||
handle_blocked "${MIMETYPE}"
|
||||
handle_fallback
|
||||
|
||||
exit 1
|
||||
|
|
|
@ -2,7 +2,7 @@
|
|||
|
||||
# Description: List files bigger than input size by ascending access date.
|
||||
#
|
||||
# Requires: find sort
|
||||
# Dependencies: find sort
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Arun Prakash Jana
|
||||
|
|
|
@ -0,0 +1,49 @@
|
|||
#!/usr/bin/env bash
|
||||
|
||||
# Description: Open selected files in nuke one by one or in oneshot
|
||||
#
|
||||
# Notes: 1. Opens the hovered file if the selection is empty
|
||||
# 2. nuke is the default, set OPENER below for custom
|
||||
# 3. Opener is invoked once for each file in a loop
|
||||
# 4. Keep pressing "Enter" to open files one by one
|
||||
#
|
||||
# Shell: bash
|
||||
# Author: Arun Prakash Jana
|
||||
|
||||
sel=${NNN_SEL:-${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.selection}
|
||||
OPENER="${XDG_CONFIG_HOME:-$HOME/.config}/nnn/plugins/nuke"
|
||||
|
||||
if [ -s "$sel" ]; then
|
||||
targets=()
|
||||
while IFS= read -r -d '' entry || [ -n "$entry" ]; do
|
||||
targets+=( "$entry" )
|
||||
done < "$sel"
|
||||
|
||||
elements=${#targets[@]}
|
||||
|
||||
if (( elements == 1 )); then
|
||||
# If there's only one file selected, open without prompts
|
||||
"$OPENER" "${targets[0]}"
|
||||
else
|
||||
printf "open [A]ll? "
|
||||
read -r all
|
||||
|
||||
for ((index=0; index <= ${#targets[@]}; index++)); do
|
||||
"$OPENER" "${targets[index]}"
|
||||
if [ "$all" != "A" ] && (( index+1 < elements )); then
|
||||
printf "press Enter to open '%s'\n" "${targets[index+1]}"
|
||||
read -r -s -n 1 key
|
||||
if [[ $key != "" ]]; then
|
||||
break
|
||||
fi
|
||||
fi
|
||||
done
|
||||
fi
|
||||
|
||||
# Clear selection
|
||||
if [ -s "$sel" ] && [ -p "$NNN_PIPE" ]; then
|
||||
printf "-" > "$NNN_PIPE"
|
||||
fi
|
||||
elif [ -n "$1" ]; then
|
||||
"$OPENER" "$1"
|
||||
fi
|
|
@ -2,43 +2,47 @@
|
|||
|
||||
# Description: Organize files in directories by category
|
||||
#
|
||||
# Note: This plugin clears the selection as it changes the contents of the current dir
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: th3lusive
|
||||
|
||||
sel=${NNN_SEL:-${XDG_CONFIG_HOME:-$HOME/.config}/nnn/.selection}
|
||||
|
||||
organize() {
|
||||
case "$(file -biL "$1")" in
|
||||
*video*)
|
||||
[ ! -d "Videos" ] && mkdir "Videos"
|
||||
mv "$1" "Videos/$1"
|
||||
mv -- "$1" "Videos/$1"
|
||||
printf "Moved %s to Videos\n" "$1" ;;
|
||||
|
||||
*audio*) [ ! -d "Audio" ] && mkdir "Audio"
|
||||
mv "$1" "Audio/$1"
|
||||
mv -- "$1" "Audio/$1"
|
||||
printf "Moved %s to Audio\n" "$1" ;;
|
||||
|
||||
*image*)
|
||||
[ ! -d "Images" ] && mkdir "Images"
|
||||
mv "$1" "Images/$1"
|
||||
mv -- "$1" "Images/$1"
|
||||
printf "Moved %s to Images\n" "$1" ;;
|
||||
|
||||
*pdf*|*document*|*epub*|*djvu*|*cb*)
|
||||
[ ! -d "Documents" ] && mkdir "Documents"
|
||||
mv "$1" "Documents/$1"
|
||||
mv -- "$1" "Documents/$1"
|
||||
printf "Moved %s to Documents\n" "$1" ;;
|
||||
|
||||
*text*)
|
||||
[ ! -d "Plaintext" ] && mkdir "Plaintext"
|
||||
mv "$1" "Plaintext/$1"
|
||||
mv -- "$1" "Plaintext/$1"
|
||||
printf "Moved %s to Plaintext\n" "$1" ;;
|
||||
|
||||
*tar*|*xz*|*compress*|*7z*|*rar*|*zip*)
|
||||
[ ! -d "Archives" ] && mkdir "Archives"
|
||||
mv "$1" "Archives/$1"
|
||||
mv -- "$1" "Archives/$1"
|
||||
printf "Moved %s to Archives\n" "$1" ;;
|
||||
|
||||
*binary*)
|
||||
[ ! -d "Binaries" ] && mkdir "Binaries"
|
||||
mv "$1" "Binaries/$1"
|
||||
mv -- "$1" "Binaries/$1"
|
||||
printf "Moved %s to Binaries\n" "$1" ;;
|
||||
esac
|
||||
}
|
||||
|
@ -48,6 +52,11 @@ main() {
|
|||
do
|
||||
[ -f "$file" ] && organize "$file"
|
||||
done
|
||||
|
||||
# Clear selection
|
||||
if [ -s "$sel" ] && [ -p "$NNN_PIPE" ]; then
|
||||
printf "-" > "$NNN_PIPE"
|
||||
fi
|
||||
}
|
||||
|
||||
main "$@"
|
||||
|
|
|
@ -5,7 +5,7 @@
|
|||
# Shell: POSIX compliant
|
||||
# Author: Arun Prakash Jana
|
||||
|
||||
if ! [ -z "$1" ]; then
|
||||
if [ -n "$1" ]; then
|
||||
tmpf="$(basename "$1")"
|
||||
tmpf="${TMPDIR:-/tmp}"/"${tmpf%.*}"
|
||||
|
||||
|
@ -15,7 +15,7 @@ if ! [ -z "$1" ]; then
|
|||
|
||||
pico2wave -w "$tmpf".wav -l en-GB "$(tr '\n' ' ' < "$tmpf".txt)"
|
||||
|
||||
rm "$tmpf".txt
|
||||
rm -- "$tmpf".txt
|
||||
else
|
||||
pico2wave -w "$tmpf".wav -l en-GB "$(tr '\n' ' ' < "$1")"
|
||||
fi
|
||||
|
@ -26,5 +26,5 @@ if ! [ -z "$1" ]; then
|
|||
# flat read but better quality
|
||||
# play -qV0 "$tmpf".wav treble 2 gain -l 2
|
||||
|
||||
rm "$tmpf".wav
|
||||
rm -- "$tmpf".wav
|
||||
fi
|
||||
|
|
|
@ -1,24 +0,0 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: View a PDF file in pager
|
||||
#
|
||||
# Notes:
|
||||
# - $PAGER must be 'less -R' or 'most'
|
||||
# - To use mutool, uncomment the relevant lines and comment the pdftotext line
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Arun Prakash Jana
|
||||
|
||||
if ! [ -z "$1" ]; then
|
||||
if [ "$(head -c 4 "$1")" = "%PDF" ]; then
|
||||
# Convert using pdftotext
|
||||
pdftotext -nopgbrk -layout "$1" - | sed 's/\xe2\x80\x8b//g' | $PAGER
|
||||
|
||||
# Convert using mutool
|
||||
# file=`basename "$1"`
|
||||
# txt=/tmp/"$file".txt
|
||||
# mutool convert -o "$txt" "$1"
|
||||
# eval $PAGER $txt
|
||||
# rm "$txt"
|
||||
fi
|
||||
fi
|
|
@ -1,26 +0,0 @@
|
|||
#!/usr/bin/env sh
|
||||
|
||||
# Description: Pick files and pipe the newline-separated list to another utility
|
||||
#
|
||||
# Shell: POSIX compliant
|
||||
# Author: Arun Prakash Jana
|
||||
#
|
||||
# Usage:
|
||||
# Copy this file in your $PATH, make it executable and preferably name it to picker.
|
||||
# Run commands like:
|
||||
# ls -l `picker`
|
||||
# cd `picker`
|
||||
# vimdiff `picker`
|
||||
# or, in fish shell:
|
||||
# ls -l (picker)
|
||||
# cd (picker)
|
||||
# vimdiff (picker)
|
||||
#
|
||||
# NOTE: This use case is limited to picking files, other functionality may not work as expected.
|
||||
|
||||
nnn -p /tmp/picked
|
||||
|
||||
if [ -f /tmp/picked ]; then
|
||||
tr '\0' '\n' < /tmp/picked
|
||||
rm /tmp/picked
|
||||
fi
|
|
@ -0,0 +1,231 @@
|
|||
#!/usr/bin/env bash
|
||||
|
||||
# Description: tabbed/xembed based file previewer
|
||||
#
|
||||
# Dependencies:
|
||||
# - tabbed (https://tools.suckless.org/tabbed): xembed host
|
||||
# - xterm (or urxvt or st or alacritty) : xembed client for text-based preview
|
||||
# - mpv (https://mpv.io): xembed client for video/audio
|
||||
# - sxiv (https://github.com/muennich/sxiv) or,
|
||||
# - nsxiv (https://codeberg.org/nsxiv/nsxiv) : xembed client for images
|
||||
# - zathura (https://pwmt.org/projects/zathura): xembed client for PDF
|
||||
# - nnn's nuke plugin for text preview and fallback
|
||||
# nuke is a fallback for 'mpv', 'sxiv'/'nsxiv', and 'zathura', but has its
|
||||
# own dependencies, see the script for more information
|
||||
# - vim (or any editor/pager really)
|
||||
# - file
|
||||
# - mktemp
|
||||
# - xdotool (optional, to keep main window focused)
|
||||
#
|
||||
# Usage:
|
||||
# - Install the dependencies. Then set a NNN_FIFO
|
||||
# and set a key for the plugin, then start `nnn`:
|
||||
# $ NNN_FIFO=/tmp/nnn.fifo nnn
|
||||
# - Launch the plugin with the designated key from nnn
|
||||
#
|
||||
# Notes:
|
||||
# 1. This plugin needs a "NNN_FIFO" to work. See man.
|
||||
# 2. If the same NNN_FIFO is used in multiple nnn instances, there will be one
|
||||
# common preview window. With different FIFO paths, they will be independent.
|
||||
# 3. This plugin only works on X, not on Wayland.
|
||||
#
|
||||
# How it works:
|
||||
# We use `tabbed` [1] as a xembed [2] host, to have a single window
|
||||
# owning each previewer window. So each previewer must be a xembed client.
|
||||
# For text previewers, this is not an issue, as there are a lot of
|
||||
# xembed-able terminal emulator (we default to `xterm`, but examples are
|
||||
# provided for `urxvt` and `st`). For graphic preview this can be trickier,
|
||||
# but a few popular viewers are xembed-able, we use:
|
||||
# - `mpv`: multimedia player, for video/audio preview
|
||||
# - `sxiv`/`nsxiv`: image viewer
|
||||
# - `zathura`: PDF viewer
|
||||
# - but we always fallback to `nuke` plugin
|
||||
#
|
||||
# [1]: https://tools.suckless.org/tabbed/
|
||||
# [2]: https://specifications.freedesktop.org/xembed-spec/xembed-spec-latest.html
|
||||
#
|
||||
# Shell: Bash (job control is weakly specified in POSIX)
|
||||
# Author: Léo Villeveygoux
|
||||
|
||||
|
||||
XDOTOOL_TIMEOUT=2
|
||||
PAGER=${PAGER:-"vim -R"}
|
||||
NUKE="${XDG_CONFIG_HOME:-$HOME/.config}/nnn/plugins/nuke"
|
||||
|
||||
if [ -n "$WAYLAND_DISPLAY" ] ; then
|
||||
echo "Wayland is not supported in preview-tabbed, this plugin could freeze your session!" >&2
|
||||
exit 1
|
||||
fi
|
||||
|
||||
if type xterm >/dev/null 2>&1 ; then
|
||||
TERMINAL="xterm -into"
|
||||
elif type urxvt >/dev/null 2>&1 ; then
|
||||
TERMINAL="urxvt -embed"
|
||||
elif type st >/dev/null 2>&1 ; then
|
||||
TERMINAL="st -w"
|
||||
elif type alacritty >/dev/null 2>&1 ; then
|
||||
TERMINAL="alacritty --embed"
|
||||
else
|
||||
echo "No xembed term found" >&2
|
||||
fi
|
||||
|
||||
if type xdg-user-dir >/dev/null 2>&1 ; then
|
||||
PICTURES_DIR=$(xdg-user-dir PICTURES)
|
||||
fi
|
||||
|
||||
term_nuke () {
|
||||
# $1 -> $XID, $2 -> $FILE
|
||||
$TERMINAL "$1" -e "$NUKE" "$2" &
|
||||
}
|
||||
|
||||
start_tabbed () {
|
||||
FIFO="$(mktemp -u)"
|
||||
mkfifo "$FIFO"
|
||||
|
||||
tabbed > "$FIFO" &
|
||||
|
||||
jobs # Get rid of the "Completed" entries
|
||||
|
||||
TABBEDPID="$(jobs -p %%)"
|
||||
|
||||
if [ -z "$TABBEDPID" ] ; then
|
||||
echo "Can't start tabbed"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
read -r XID < "$FIFO"
|
||||
|
||||
rm -- "$FIFO"
|
||||
}
|
||||
|
||||
get_viewer_pid () {
|
||||
VIEWERPID="$(jobs -p %%)"
|
||||
}
|
||||
|
||||
kill_viewer () {
|
||||
if [ -n "$VIEWERPID" ] && jobs -p | grep "$VIEWERPID" ; then
|
||||
kill "$VIEWERPID"
|
||||
fi
|
||||
}
|
||||
|
||||
sigint_kill () {
|
||||
kill_viewer
|
||||
kill "$TABBEDPID"
|
||||
exit 0
|
||||
}
|
||||
|
||||
previewer_loop () {
|
||||
unset -v NNN_FIFO
|
||||
# mute from now
|
||||
exec >/dev/null 2>&1
|
||||
|
||||
MAINWINDOW="$(xdotool getactivewindow)"
|
||||
|
||||
start_tabbed
|
||||
trap sigint_kill SIGINT
|
||||
|
||||
xdotool windowactivate "$MAINWINDOW"
|
||||
|
||||
# Bruteforce focus stealing prevention method,
|
||||
# works well in floating window managers like XFCE
|
||||
# but make interaction with the preview window harder
|
||||
# (uncomment to use):
|
||||
#xdotool behave "$XID" focus windowactivate "$MAINWINDOW" &
|
||||
|
||||
while read -r FILE ; do
|
||||
|
||||
jobs # Get rid of the "Completed" entries
|
||||
|
||||
if ! jobs | grep tabbed ; then
|
||||
break
|
||||
fi
|
||||
|
||||
if [ ! -e "$FILE" ] ; then
|
||||
continue
|
||||
fi
|
||||
|
||||
kill_viewer
|
||||
|
||||
MIME="$(file -bL --mime-type "$FILE")"
|
||||
|
||||
case "$MIME" in
|
||||
video/*)
|
||||
if type mpv >/dev/null 2>&1 ; then
|
||||
mpv --force-window=immediate --loop-file --wid="$XID" "$FILE" &
|
||||
else
|
||||
term_nuke "$XID" "$FILE"
|
||||
fi
|
||||
;;
|
||||
audio/*)
|
||||
if type mpv >/dev/null 2>&1 ; then
|
||||
mpv --force-window=immediate --loop-file --wid="$XID" "$FILE" &
|
||||
else
|
||||
term_nuke "$XID" "$FILE"
|
||||
fi
|
||||
;;
|
||||
image/*)
|
||||
if type sxiv >/dev/null 2>&1 ; then
|
||||
sxiv -ae "$XID" "$FILE" &
|
||||
elif type nsxiv >/dev/null 2>&1 ; then
|
||||
nsxiv -ae "$XID" "$FILE" &
|
||||
else
|
||||
term_nuke "$XID" "$FILE"
|
||||
fi
|
||||
;;
|
||||
application/pdf)
|
||||
if type zathura >/dev/null 2>&1 ; then
|
||||
zathura -e "$XID" "$FILE" &
|
||||
else
|
||||
term_nuke "$XID" "$FILE"
|
||||
fi
|
||||
;;
|
||||
inode/directory)
|
||||
if [[ -n $PICTURES_DIR && "$FILE" == "$PICTURES_DIR"* ]] ; then
|
||||
if type sxiv >/dev/null 2>&1 ; then
|
||||
sxiv -te "$XID" "$FILE" &
|
||||
elif type nsxiv >/dev/null 2>&1 ; then
|
||||
nsxiv -te "$XID" "$FILE" &
|
||||
else
|
||||
$TERMINAL "$XID" -e nnn "$FILE" &
|
||||
fi
|
||||
else
|
||||
$TERMINAL "$XID" -e nnn "$FILE" &
|
||||
fi
|
||||
;;
|
||||
text/*)
|
||||
if [ -x "$NUKE" ] ; then
|
||||
term_nuke "$XID" "$FILE"
|
||||
else
|
||||
# shellcheck disable=SC2086
|
||||
$TERMINAL "$XID" -e $PAGER "$FILE" &
|
||||
fi
|
||||
;;
|
||||
*)
|
||||
if [ -x "$NUKE" ] ; then
|
||||
term_nuke "$XID" "$FILE"
|
||||
else
|
||||
$TERMINAL "$XID" -e sh -c "file '$FILE' | $PAGER -" &
|
||||
fi
|
||||
;;
|
||||
esac
|
||||
get_viewer_pid
|
||||
|
||||
# following lines are not needed with the bruteforce xdotool method
|
||||
ACTIVE_XID="$(xdotool getactivewindow)"
|
||||
if [ $((ACTIVE_XID == XID)) -ne 0 ] ; then
|
||||
xdotool windowactivate "$MAINWINDOW"
|
||||
else
|
||||
timeout "$XDOTOOL_TIMEOUT" xdotool behave "$XID" focus windowactivate "$MAINWINDOW" &
|
||||
fi
|
||||
done
|
||||
kill "$TABBEDPID"
|
||||
kill_viewer
|
||||
}
|
||||
|
||||
if [ ! -r "$NNN_FIFO" ] ; then
|
||||
echo "Can't read \$NNN_FIFO ('$NNN_FIFO')"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
previewer_loop < "$NNN_FIFO" &
|
||||
disown
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue