Ecosyste.ms: Awesome
An open API service indexing awesome lists of open source software.
https://github.com/nvim-treesitter/nvim-treesitter-textobjects
https://github.com/nvim-treesitter/nvim-treesitter-textobjects
hacktoberfest lua neovim nvim tree-sitter
Last synced: 6 days ago
JSON representation
- Host: GitHub
- URL: https://github.com/nvim-treesitter/nvim-treesitter-textobjects
- Owner: nvim-treesitter
- License: apache-2.0
- Created: 2020-09-20T14:53:24.000Z (over 4 years ago)
- Default Branch: master
- Last Pushed: 2025-01-28T10:44:13.000Z (14 days ago)
- Last Synced: 2025-02-02T20:29:52.061Z (9 days ago)
- Topics: hacktoberfest, lua, neovim, nvim, tree-sitter
- Language: Scheme
- Homepage:
- Size: 587 KB
- Stars: 2,267
- Watchers: 11
- Forks: 204
- Open Issues: 104
-
Metadata Files:
- Readme: README.md
- Contributing: CONTRIBUTING.md
- License: LICENSE
Awesome Lists containing this project
- awesome-neovim - nvim-treesitter/nvim-treesitter-textobjects - Create your own textobjects using Tree-sitter queries. (Syntax / PHP)
README
# nvim-treesitter-textobjects
Syntax aware text-objects, select, move, swap, and peek support.
**Warning: tree-sitter and nvim-treesitter are an experimental feature of nightly versions of Neovim.
Please consider the experience with this plug-in as experimental until tree-sitter support in Neovim is stable!
We recommend using the nightly builds of Neovim or the latest stable version.**## Installation
You can install nvim-treesitter-textobjects with your favorite package manager, or using the default pack feature of Neovim!
### Using a package manager
If you are using [vim-plug](https://github.com/junegunn/vim-plug), put this in your init.vim file:
```vim
Plug 'nvim-treesitter/nvim-treesitter', {'do': ':TSUpdate'}
Plug 'nvim-treesitter/nvim-treesitter-textobjects'
```If you are using [Packer](https://github.com/wbthomason/packer.nvim), put it in your init.lua file:
```lua
use({
"nvim-treesitter/nvim-treesitter-textobjects",
after = "nvim-treesitter",
requires = "nvim-treesitter/nvim-treesitter",
})
```## Text objects: select
Define your own text objects mappings
similar to `ip` (inner paragraph) and `ap` (a paragraph).```lua
lua <') or a table
-- mapping query_strings to modes.
selection_modes = {
['@parameter.outer'] = 'v', -- charwise
['@function.outer'] = 'V', -- linewise
['@class.outer'] = '', -- blockwise
},
-- If you set this to `true` (default is `false`) then any textobject is
-- extended to include preceding or succeeding whitespace. Succeeding
-- whitespace has priority in order to act similarly to eg the built-in
-- `ap`.
--
-- Can also be a function which gets passed a table with the keys
-- * query_string: eg '@function.inner'
-- * selection_mode: eg 'v'
-- and should return true or false
include_surrounding_whitespace = true,
},
},
}
EOF
```## Text objects: swap
Define your own mappings to swap the node under the cursor with the next or previous one,
like function parameters or arguments.```lua
lua <a"] = "@parameter.inner",
},
swap_previous = {
["A"] = "@parameter.inner",
},
},
},
}
EOF
```## Text objects: move
Define your own mappings to jump to the next or previous text object.
This is similar to `]m`, `[m`, `]M`, `[M` Neovim's mappings to jump to the next
or previous function.```lua
lua </.scm file in your runtime path.
-- Below example nvim-treesitter's `locals.scm` and `folds.scm`. They also provide highlights.scm and indent.scm.
["]s"] = { query = "@local.scope", query_group = "locals", desc = "Next scope" },
["]z"] = { query = "@fold", query_group = "folds", desc = "Next fold" },
},
goto_next_end = {
["]M"] = "@function.outer",
["]["] = "@class.outer",
},
goto_previous_start = {
["[m"] = "@function.outer",
["[["] = "@class.outer",
},
goto_previous_end = {
["[M"] = "@function.outer",
["[]"] = "@class.outer",
},
-- Below will go to either the start or the end, whichever is closer.
-- Use if you want more granular movements
-- Make it even more gradual by adding multiple queries and regex.
goto_next = {
["]d"] = "@conditional.outer",
},
goto_previous = {
["[d"] = "@conditional.outer",
}
},
},
}
EOF
```You can make the movements repeatable like `;` and `,`.
```lua
local ts_repeat_move = require "nvim-treesitter.textobjects.repeatable_move"-- Repeat movement with ; and ,
-- ensure ; goes forward and , goes backward regardless of the last direction
vim.keymap.set({ "n", "x", "o" }, ";", ts_repeat_move.repeat_last_move_next)
vim.keymap.set({ "n", "x", "o" }, ",", ts_repeat_move.repeat_last_move_previous)-- vim way: ; goes to the direction you were moving.
-- vim.keymap.set({ "n", "x", "o" }, ";", ts_repeat_move.repeat_last_move)
-- vim.keymap.set({ "n", "x", "o" }, ",", ts_repeat_move.repeat_last_move_opposite)-- Optionally, make builtin f, F, t, T also repeatable with ; and ,
vim.keymap.set({ "n", "x", "o" }, "f", ts_repeat_move.builtin_f_expr, { expr = true })
vim.keymap.set({ "n", "x", "o" }, "F", ts_repeat_move.builtin_F_expr, { expr = true })
vim.keymap.set({ "n", "x", "o" }, "t", ts_repeat_move.builtin_t_expr, { expr = true })
vim.keymap.set({ "n", "x", "o" }, "T", ts_repeat_move.builtin_T_expr, { expr = true })
```You can even make a custom repeat behaviour.
```lua
-- This repeats the last query with always previous direction and to the start of the range.
vim.keymap.set({ "n", "x", "o" }, "", function()
ts_repeat_move.repeat_last_move({forward = false, start = true})
end)-- This repeats the last query with always next direction and to the end of the range.
vim.keymap.set({ "n", "x", "o" }, "", function()
ts_repeat_move.repeat_last_move({forward = true, start = false})
end)
```Furthermore, you can make any custom movements (e.g. from another plugin) repeatable with the same keys.
This doesn't need to be treesitter-related.```lua
-- example: make gitsigns.nvim movement repeatable with ; and , keys.
local gs = require("gitsigns")-- make sure forward function comes first
local next_hunk_repeat, prev_hunk_repeat = ts_repeat_move.make_repeatable_move_pair(gs.next_hunk, gs.prev_hunk)
-- Or, use `make_repeatable_move` or `set_last_move` functions for more control. See the code for instructions.vim.keymap.set({ "n", "x", "o" }, "]h", next_hunk_repeat)
vim.keymap.set({ "n", "x", "o" }, "[h", prev_hunk_repeat)
```Alternative way is to use a repeatable movement managing plugin such as [nvim-next](https://github.com/ghostbuster91/nvim-next).
## Textobjects: LSP interop
- peek_definition_code: show textobject surrounding definition as determined
using Neovim's built-in LSP in a floating window. Press the shortcut twice
to enter the floating window.```lua
lua <df"] = "@function.outer",
["dF"] = "@class.outer",
},
},
},
}
EOF
```# Overriding or extending textobjects
Textobjects are defined in the `textobjects.scm` files.
You can extend or override those files by following the instructions at
.
You can also use a custom capture for your own textobjects,
and use it in any of the textobject modules, for example:```scm
-- after/queries/python/textobjects.scm
; extends
(function_definition) @custom_capture
``````lua
lua <
1. @assignment.inner
2. @assignment.lhs
3. @assignment.outer
4. @assignment.rhs
5. @attribute.inner
6. @attribute.outer
7. @block.inner
8. @block.outer
9. @call.inner
10. @call.outer
11. @class.inner
12. @class.outer
13. @comment.inner
14. @comment.outer
15. @conditional.inner
16. @conditional.outer
17. @frame.inner
18. @frame.outer
19. @function.inner
20. @function.outer
21. @loop.inner
22. @loop.outer
23. @number.inner
24. @parameter.inner
25. @parameter.outer
26. @regex.inner
27. @regex.outer
28. @return.inner
29. @return.outer
30. @scopename.inner
31. @statement.outer1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31
apex🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
astro⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ 🟩 ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
bash🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩 ⬜ ⬜ ⬜ ⬜ ⬜
bibtex⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩
c🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 ⬜ 🟩
c_sharp⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
cmake⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
cpp🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 ⬜ 🟩
css🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
cuda🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 ⬜ 🟩
dart⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ 🟩
dockerfile⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
elixir⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ ⬜
elm⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
fennel🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ 🟩
fish🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ 🟩 ⬜ 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩 ⬜ ⬜ 🟩 🟩 ⬜ 🟩
foam⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
glsl🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 ⬜ 🟩
go🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ 🟩
hack⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
haskell⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
hcl🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ 🟩 🟩 🟩 ⬜ ⬜ ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ 🟩
heex⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
hlsl🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 ⬜ 🟩
html⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ 🟩 ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
inko🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 ⬜ ⬜
java⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
javascript🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩
julia🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ ⬜
kotlin⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
latex⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
lua🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 ⬜ ⬜
matlab⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 ⬜ 🟩
nasm⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ 🟩 ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
nim🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 ⬜ 🟩
nix⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
odin🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩 ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 ⬜ ⬜
perl⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 ⬜ ⬜ ⬜ ⬜
php⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ 🟩
php_only⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ 🟩
python🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 ⬜ 🟩
ql⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 ⬜
r🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ 🟩
readline⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩
rst⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ 🟩 🟩 ⬜ 🟩 ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
ruby⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ 🟩 🟩 ⬜ 🟩 ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ ⬜
rust🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 ⬜ 🟩
scala⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
scss🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
slang🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 ⬜ 🟩
supercollider⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ 🟩 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
swift⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ 🟩 ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
tact🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 ⬜ ⬜
terraform🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ 🟩 🟩 🟩 ⬜ ⬜ ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ 🟩
toml⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
tsx🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩
twig⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ 🟩
typescript🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩
v🟩 🟩 ⬜ 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 ⬜ 🟩
verilog⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
vim🟩 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 ⬜ 🟩 ⬜ ⬜ ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩
vue⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 ⬜ ⬜ ⬜ ⬜ 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
wgsl⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 ⬜ ⬜ 🟩 🟩 ⬜ ⬜ 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
wgsl_bevy⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 ⬜ ⬜ 🟩 🟩 ⬜ ⬜ 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜
yaml🟩 🟩 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩
zig⬜ ⬜ ⬜ ⬜ ⬜ ⬜ 🟩 🟩 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 🟩 ⬜ ⬜ 🟩 🟩 🟩 🟩 ⬜ 🟩 🟩 ⬜ ⬜ ⬜ ⬜ ⬜ 🟩