Files
nvim/lua/plugins/colorscheme.lua
zias 6ec8190beb refactor: modularize nvim config into lua/config + lua/plugins
- Extract all options, keymaps, and autocommands into lua/config/
- Move every plugin spec into its own file under lua/plugins/
- Add custom inline orng colorscheme (dark + light) synced to macOS appearance
- Consolidate image.nvim into pdf-viewer.lua (fix duplicate spec)
- Fix image.nvim processor: magick -> magick_cli
- Remove conflicting nvim-autopairs (kept mini.pairs)
- Fix broken <C-f> keymap (was calling non-existent builtin cmd)
- Delete lua/kickstart/ and lua/custom/ folders
- Add colors/orng.vim + colors/orng-light.vim stubs for mid-session switching
- init.lua reduced from 1078 lines to 49 lines
2026-02-26 11:54:58 +01:00

369 lines
16 KiB
Lua

-- lua/plugins/colorscheme.lua
-- Custom "orng" colorscheme — dark and light variants.
-- Palette source: https://gist.github.com/axeldotdev/9b441e22147d2d838624d82357ac4302
--
-- Usage:
-- :colorscheme orng → dark (bg #0a0a0a)
-- :colorscheme orng-light → light (bg #ffffff)
-- ── Shared accent colors ───────────────────────────────────────────────────
local accent = {
orange = '#EC5B2B',
orange_br = '#EE7948',
cyan = '#56b6c2',
red = '#e06c75',
}
-- ── Dark palette ───────────────────────────────────────────────────────────
local dark = {
bg = '#0a0a0a',
fg = '#eeeeee',
orange = accent.orange,
orange_br = accent.orange_br,
yellow = '#e5c07b',
yellow_br = '#FFF7F1',
blue = '#6ba1e6',
cyan = accent.cyan,
red = accent.red,
gray1 = '#1a1a1a', -- panel / float bg
gray2 = '#2a2a2a', -- prompt bg
gray3 = '#3a3a3a', -- borders / separators
gray4 = '#606060', -- comments / inactive
gray5 = '#888888', -- delimiters
sel_bg = accent.orange,
sel_fg = '#0a0a0a',
diff_add = '#0d1f2d',
diff_chg = '#1f1a0d',
diff_del = '#1f0d0d',
diff_txt = '#2a1a0a',
vt_err = '#1f0d0d',
vt_warn = '#1f1a0d',
vt_info = '#0d1020',
vt_hint = '#0d1a1a',
}
-- ── Light palette ──────────────────────────────────────────────────────────
local light = {
bg = '#ffffff',
fg = '#1a1a1a',
orange = '#D44A1A', -- slightly darker than accent for readability on white
orange_br = accent.orange,
yellow = '#b07800',
yellow_br = '#8a5c00',
blue = '#2d6fc4',
cyan = '#1a7a87',
red = '#c0334a',
gray1 = '#f5f0eb', -- panel / float bg (warm off-white)
gray2 = '#ede8e2', -- prompt bg
gray3 = '#d4cfc8', -- borders / separators
gray4 = '#999999', -- comments / inactive
gray5 = '#777777', -- delimiters
sel_bg = accent.orange,
sel_fg = '#ffffff',
diff_add = '#ddeeff',
diff_chg = '#fff3cc',
diff_del = '#ffd6d6',
diff_txt = '#ffe0b2',
vt_err = '#fde8e8',
vt_warn = '#fef9e0',
vt_info = '#e8f0fd',
vt_hint = '#e0f5f5',
}
-- ── Highlight helper ───────────────────────────────────────────────────────
local function hi(group, opts)
vim.api.nvim_set_hl(0, group, opts)
end
-- ── Apply function — called with either `dark` or `light` palette ──────────
local function apply(c, variant)
local bg_mode = variant == 'light' and 'light' or 'dark'
vim.o.background = bg_mode
vim.cmd.highlight 'clear'
if vim.fn.exists 'syntax_on' == 1 then vim.cmd.syntax 'reset' end
vim.g.colors_name = 'orng' .. (variant == 'light' and '-light' or '')
-- Editor chrome
hi('Normal', { fg = c.fg, bg = c.bg })
hi('NormalFloat', { fg = c.fg, bg = c.gray1 })
hi('NormalNC', { fg = c.fg, bg = c.bg })
hi('FloatBorder', { fg = c.orange, bg = c.gray1 })
hi('FloatTitle', { fg = c.orange_br, bg = c.gray1, bold = true })
hi('ColorColumn', { bg = c.gray1 })
hi('CursorLine', { bg = c.gray1 })
hi('CursorLineNr', { fg = c.orange, bold = true })
hi('LineNr', { fg = c.gray4 })
hi('SignColumn', { fg = c.gray4, bg = c.bg })
hi('Folded', { fg = c.gray4, bg = c.gray1 })
hi('FoldColumn', { fg = c.gray4, bg = c.bg })
hi('VertSplit', { fg = c.gray3 })
hi('WinSeparator', { fg = c.gray3 })
hi('EndOfBuffer', { fg = c.gray3 })
-- Cursor & selection
hi('Cursor', { fg = c.bg, bg = c.fg })
hi('CursorIM', { fg = c.bg, bg = c.fg })
hi('Visual', { fg = c.sel_fg, bg = c.sel_bg })
hi('VisualNOS', { fg = c.sel_fg, bg = c.sel_bg })
-- Status / tab line
hi('StatusLine', { fg = c.fg, bg = c.gray2 })
hi('StatusLineNC', { fg = c.gray4, bg = c.gray1 })
hi('TabLine', { fg = c.gray4, bg = c.gray1 })
hi('TabLineFill', { bg = c.gray1 })
hi('TabLineSel', { fg = c.fg, bg = c.gray2, bold = true })
-- Pmenu
hi('Pmenu', { fg = c.fg, bg = c.gray1 })
hi('PmenuSel', { fg = c.sel_fg, bg = c.orange })
hi('PmenuSbar', { bg = c.gray2 })
hi('PmenuThumb', { bg = c.orange })
hi('PmenuBorder', { fg = c.orange })
-- Search
hi('Search', { fg = c.bg, bg = c.yellow })
hi('IncSearch', { fg = c.bg, bg = c.orange })
hi('CurSearch', { fg = c.bg, bg = c.orange_br })
hi('Substitute', { fg = c.bg, bg = c.orange })
-- Messages
hi('ErrorMsg', { fg = c.red, bold = true })
hi('WarningMsg', { fg = c.yellow })
hi('ModeMsg', { fg = c.orange, bold = true })
hi('MoreMsg', { fg = c.orange })
hi('Question', { fg = c.blue })
-- Diff
hi('DiffAdd', { fg = c.blue, bg = c.diff_add })
hi('DiffChange', { fg = c.yellow, bg = c.diff_chg })
hi('DiffDelete', { fg = c.red, bg = c.diff_del })
hi('DiffText', { fg = c.orange_br, bg = c.diff_txt, bold = true })
hi('Added', { fg = c.blue })
hi('Changed', { fg = c.yellow })
hi('Removed', { fg = c.red })
-- Spelling
hi('SpellBad', { undercurl = true, sp = c.red })
hi('SpellCap', { undercurl = true, sp = c.yellow })
hi('SpellLocal', { undercurl = true, sp = c.blue })
hi('SpellRare', { undercurl = true, sp = c.cyan })
-- Syntax
hi('Comment', { fg = c.gray4, italic = true })
hi('Constant', { fg = c.orange_br })
hi('String', { fg = c.yellow_br })
hi('Character', { fg = c.yellow_br })
hi('Number', { fg = c.orange_br })
hi('Boolean', { fg = c.orange, bold = true })
hi('Float', { fg = c.orange_br })
hi('Identifier', { fg = c.fg })
hi('Function', { fg = c.orange, bold = true })
hi('Statement', { fg = c.orange })
hi('Conditional', { fg = c.orange })
hi('Repeat', { fg = c.orange })
hi('Label', { fg = c.orange })
hi('Operator', { fg = c.yellow })
hi('Keyword', { fg = c.orange, bold = true })
hi('Exception', { fg = c.red })
hi('PreProc', { fg = c.blue })
hi('Include', { fg = c.blue })
hi('Define', { fg = c.blue })
hi('Macro', { fg = c.blue })
hi('PreCondit', { fg = c.blue })
hi('Type', { fg = c.yellow })
hi('StorageClass', { fg = c.yellow })
hi('Structure', { fg = c.yellow })
hi('Typedef', { fg = c.yellow })
hi('Special', { fg = c.cyan })
hi('SpecialChar', { fg = c.cyan })
hi('Tag', { fg = c.orange })
hi('Delimiter', { fg = c.gray5 })
hi('SpecialComment', { fg = c.gray4, italic = true })
hi('Debug', { fg = c.red })
hi('Underlined', { underline = true })
hi('Ignore', { fg = c.gray4 })
hi('Error', { fg = c.red, bold = true })
hi('Todo', { fg = c.bg, bg = c.orange, bold = true })
-- Treesitter
hi('@variable', { fg = c.fg })
hi('@variable.builtin', { fg = c.orange_br })
hi('@variable.parameter', { fg = c.fg })
hi('@variable.member', { fg = c.fg })
hi('@constant', { fg = c.orange_br })
hi('@constant.builtin', { fg = c.orange, bold = true })
hi('@constant.macro', { fg = c.blue })
hi('@string', { fg = c.yellow_br })
hi('@string.escape', { fg = c.cyan })
hi('@string.special', { fg = c.cyan })
hi('@character', { fg = c.yellow_br })
hi('@number', { fg = c.orange_br })
hi('@boolean', { fg = c.orange, bold = true })
hi('@float', { fg = c.orange_br })
hi('@function', { fg = c.orange, bold = true })
hi('@function.builtin', { fg = c.orange_br })
hi('@function.call', { fg = c.orange })
hi('@function.macro', { fg = c.blue })
hi('@function.method', { fg = c.orange })
hi('@function.method.call', { fg = c.orange })
hi('@constructor', { fg = c.yellow })
hi('@operator', { fg = c.yellow })
hi('@keyword', { fg = c.orange, bold = true })
hi('@keyword.function', { fg = c.orange, bold = true })
hi('@keyword.operator', { fg = c.yellow })
hi('@keyword.return', { fg = c.orange, bold = true })
hi('@keyword.import', { fg = c.blue })
hi('@keyword.conditional', { fg = c.orange })
hi('@keyword.repeat', { fg = c.orange })
hi('@keyword.exception', { fg = c.red })
hi('@type', { fg = c.yellow })
hi('@type.builtin', { fg = c.yellow, bold = true })
hi('@type.definition', { fg = c.yellow })
hi('@attribute', { fg = c.blue })
hi('@property', { fg = c.fg })
hi('@punctuation.delimiter', { fg = c.gray5 })
hi('@punctuation.bracket', { fg = c.gray5 })
hi('@punctuation.special', { fg = c.cyan })
hi('@comment', { fg = c.gray4, italic = true })
hi('@comment.documentation', { fg = c.gray5, italic = true })
hi('@tag', { fg = c.orange })
hi('@tag.attribute', { fg = c.yellow })
hi('@tag.delimiter', { fg = c.gray5 })
hi('@markup.heading', { fg = c.orange, bold = true })
hi('@markup.bold', { fg = c.yellow_br, bold = true })
hi('@markup.italic', { fg = c.fg, italic = true })
hi('@markup.link', { fg = c.blue, underline = true })
hi('@markup.link.url', { fg = c.blue, underline = true })
hi('@markup.raw', { fg = c.cyan })
hi('@markup.list', { fg = c.orange })
-- LSP
hi('LspReferenceText', { bg = c.gray2 })
hi('LspReferenceRead', { bg = c.gray2 })
hi('LspReferenceWrite', { bg = c.gray3 })
hi('LspInlayHint', { fg = c.gray4, italic = true })
hi('LspCodeLens', { fg = c.gray4, italic = true })
-- Diagnostics
hi('DiagnosticError', { fg = c.red })
hi('DiagnosticWarn', { fg = c.yellow })
hi('DiagnosticInfo', { fg = c.blue })
hi('DiagnosticHint', { fg = c.cyan })
hi('DiagnosticOk', { fg = c.blue })
hi('DiagnosticVirtualTextError', { fg = c.red, bg = c.vt_err, italic = true })
hi('DiagnosticVirtualTextWarn', { fg = c.yellow, bg = c.vt_warn, italic = true })
hi('DiagnosticVirtualTextInfo', { fg = c.blue, bg = c.vt_info, italic = true })
hi('DiagnosticVirtualTextHint', { fg = c.cyan, bg = c.vt_hint, italic = true })
hi('DiagnosticUnderlineError', { undercurl = true, sp = c.red })
hi('DiagnosticUnderlineWarn', { undercurl = true, sp = c.yellow })
hi('DiagnosticUnderlineInfo', { undercurl = true, sp = c.blue })
hi('DiagnosticUnderlineHint', { undercurl = true, sp = c.cyan })
-- Gitsigns
hi('GitSignsAdd', { fg = c.blue })
hi('GitSignsChange', { fg = c.yellow })
hi('GitSignsDelete', { fg = c.red })
-- Telescope
hi('TelescopeBorder', { fg = c.orange, bg = c.gray1 })
hi('TelescopeNormal', { fg = c.fg, bg = c.gray1 })
hi('TelescopePromptBorder', { fg = c.orange_br, bg = c.gray2 })
hi('TelescopePromptNormal', { fg = c.fg, bg = c.gray2 })
hi('TelescopePromptPrefix', { fg = c.orange, bg = c.gray2 })
hi('TelescopeResultsBorder', { fg = c.orange, bg = c.gray1 })
hi('TelescopePreviewBorder', { fg = c.gray3, bg = c.gray1 })
hi('TelescopeSelection', { fg = c.sel_fg, bg = c.orange })
hi('TelescopeSelectionCaret', { fg = c.sel_fg, bg = c.orange })
hi('TelescopeMatching', { fg = c.orange_br, bold = true })
hi('TelescopeTitle', { fg = c.orange_br, bold = true })
-- NeoTree
hi('NeoTreeNormal', { fg = c.fg, bg = c.gray1 })
hi('NeoTreeNormalNC', { fg = c.fg, bg = c.gray1 })
hi('NeoTreeVertSplit', { fg = c.gray3, bg = c.gray1 })
hi('NeoTreeWinSeparator', { fg = c.gray3, bg = c.gray1 })
hi('NeoTreeDirectoryName',{ fg = c.orange })
hi('NeoTreeDirectoryIcon',{ fg = c.orange })
hi('NeoTreeFileName', { fg = c.fg })
hi('NeoTreeGitAdded', { fg = c.blue })
hi('NeoTreeGitModified', { fg = c.yellow })
hi('NeoTreeGitDeleted', { fg = c.red })
hi('NeoTreeIndentMarker', { fg = c.gray3 })
hi('NeoTreeExpander', { fg = c.orange })
hi('NeoTreeTitleBar', { fg = c.bg, bg = c.orange, bold = true })
-- Which-key
hi('WhichKey', { fg = c.orange })
hi('WhichKeyGroup', { fg = c.yellow })
hi('WhichKeyDesc', { fg = c.fg })
hi('WhichKeySeparator', { fg = c.gray4 })
hi('WhichKeyFloat', { bg = c.gray1 })
hi('WhichKeyBorder', { fg = c.orange, bg = c.gray1 })
-- Blink.cmp
hi('BlinkCmpMenu', { fg = c.fg, bg = c.gray1 })
hi('BlinkCmpMenuBorder', { fg = c.orange, bg = c.gray1 })
hi('BlinkCmpMenuSelection', { fg = c.sel_fg, bg = c.orange })
hi('BlinkCmpScrollBarThumb', { bg = c.orange })
hi('BlinkCmpScrollBarGutter', { bg = c.gray2 })
hi('BlinkCmpLabel', { fg = c.fg })
hi('BlinkCmpLabelMatch', { fg = c.orange_br, bold = true })
hi('BlinkCmpKind', { fg = c.yellow })
hi('BlinkCmpDoc', { fg = c.fg, bg = c.gray1 })
hi('BlinkCmpDocBorder', { fg = c.gray3, bg = c.gray1 })
-- Mini.statusline
hi('MiniStatuslineModeNormal', { fg = c.bg, bg = c.orange, bold = true })
hi('MiniStatuslineModeInsert', { fg = c.bg, bg = c.blue, bold = true })
hi('MiniStatuslineModeVisual', { fg = c.bg, bg = c.yellow, bold = true })
hi('MiniStatuslineModeReplace', { fg = c.bg, bg = c.red, bold = true })
hi('MiniStatuslineModeCommand', { fg = c.bg, bg = c.orange_br, bold = true })
hi('MiniStatuslineModeOther', { fg = c.bg, bg = c.gray4, bold = true })
hi('MiniStatuslineDevinfo', { fg = c.fg, bg = c.gray2 })
hi('MiniStatuslineFilename', { fg = c.fg, bg = c.gray2 })
hi('MiniStatuslineFileinfo', { fg = c.fg, bg = c.gray2 })
hi('MiniStatuslineInactive', { fg = c.gray4, bg = c.gray1 })
-- Todo-comments
hi('TodoBgTODO', { fg = c.bg, bg = c.orange, bold = true })
hi('TodoBgNOTE', { fg = c.bg, bg = c.blue, bold = true })
hi('TodoBgFIX', { fg = c.bg, bg = c.red, bold = true })
hi('TodoBgWARN', { fg = c.bg, bg = c.yellow, bold = true })
hi('TodoBgHACK', { fg = c.bg, bg = c.yellow, bold = true })
hi('TodoBgPERF', { fg = c.bg, bg = c.cyan, bold = true })
hi('TodoFgTODO', { fg = c.orange })
hi('TodoFgNOTE', { fg = c.blue })
hi('TodoFgFIX', { fg = c.red })
hi('TodoFgWARN', { fg = c.yellow })
hi('TodoFgHACK', { fg = c.yellow })
hi('TodoFgPERF', { fg = c.cyan })
end
-- ── Helper: pick palette from macOS system appearance ─────────────────────
local function is_dark_mode()
local out = vim.fn.system 'defaults read -g AppleInterfaceStyle 2>/dev/null'
return out:match 'Dark' ~= nil
end
-- ── Apply on startup based on system appearance ────────────────────────────
if is_dark_mode() then
apply(dark, 'dark')
else
apply(light, 'light')
end
-- ── Re-apply on explicit :colorscheme calls ────────────────────────────────
-- These autocmds let :colorscheme orng / orng-light work mid-session.
-- Note: they fire only if a colors/orng*.vim stub exists; we create one below.
vim.api.nvim_create_autocmd('ColorScheme', {
pattern = 'orng',
callback = function() apply(dark, 'dark') end,
})
vim.api.nvim_create_autocmd('ColorScheme', {
pattern = 'orng-light',
callback = function() apply(light, 'light') end,
})
return {}