├── .gitignore ├── LICENSE ├── README.md ├── chroma.lua └── img └── example_output.png /.gitignore: -------------------------------------------------------------------------------- 1 | # Object files 2 | *.o 3 | *.ko 4 | *.obj 5 | *.elf 6 | 7 | # Libraries 8 | *.lib 9 | *.a 10 | 11 | # Shared objects (inc. Windows DLLs) 12 | *.dll 13 | *.so 14 | *.so.* 15 | *.dylib 16 | 17 | # Executables 18 | *.exe 19 | *.out 20 | *.app 21 | *.i*86 22 | *.x86_64 23 | *.hex 24 | example.lua 25 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | 3 | Copyright (c) 2014 ldrumm 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | lua-chroma 2 | ========== 3 | 4 | Simple colour text printing for ANSI compatible terminals. 5 | 6 | Lua5.1, 5.2, 5.3 luajit2 7 | 8 | Install with `luarocks install chroma` 9 | 10 | This project is an attempt to simplify colour test formatting 11 | on ANSI mode consoles allowing easy data-driven formatting of text. 12 | 13 |

Example

14 | 15 | ```lua 16 | --[[ Here we are overriding the standard Lua print function. 17 | All existing print() calls will continue to work normally, though, so 18 | this is probably a safe override. 19 | ]] 20 | print = require("chroma") 21 | 22 | --Let's print a scary greeting 23 | print.red("hello, world!") 24 | 25 | --Perhaps that wasn't aggressive enough? 26 | print.red.underline.bold("I said 'Hello, World!...'\n\n") 27 | --Maybe that was too much; perhaps a cooler tone? 28 | print.blue.bold.highlight.navy("Oh, I'm afraid I just blue myself") 29 | 30 | --[[ We can also do that in a different order because the formatting 31 | table indexes are generated dynamically 32 | ]] 33 | print.bold.green("Such a poor choice of words\n\n") 34 | --Let's print today's headline 35 | 36 | print.highlight.gray(string.rep(' ', 80)) 37 | print.yellow.bold.underline.highlight.navy("Do you know the muffin man?") 38 | print.highlight.gray(string.rep(' ', 80)..'\n\n') 39 | 40 | --If we want to just use print as normal, then why not? 41 | print('"Normal Printing never seemed so possible"') 42 | print('\n\n') 43 | 44 | --[[Perhaps the best part of using the library, is the dynamic lookups, 45 | which allow us to autoformat code. Take the following text from wikipedia' 46 | https://en.wikipedia.org/wiki/Colours#Color_naming 47 | ]] 48 | 49 | wiki = [[ 50 | Colors vary in several different ways, including hue (shades of red, 51 | orange, yellow, green, blue, and violet), saturation, brightness, and 52 | gloss. Some color words are derived from the name of an object of that 53 | color, such as "orange" or "salmon", while others are abstract, like "red". 54 | 55 | In the 1969 study Basic Color Terms: Their Universality and Evolution, Brent 56 | Berlin and Paul Kay describe a pattern in naming "basic" colors (like "red" but 57 | not "red-orange" or "dark red" or "blood red", which are "shades" of red). All 58 | languages that have two "basic" color names distinguish dark/cool colors from 59 | bright/warm colors. The next colors to be distinguished are usually red and then 60 | yellow or green. All languages with six "basic" colors include black, white, 61 | red, green, blue, and yellow. The pattern holds up to a set of twelve: black, 62 | gray, white, pink, red, orange, yellow, green, blue, purple, brown, and azure 63 | (distinct from blue in Russian and Italian, but not English). 64 | ]] 65 | 66 | print.print = function(s) return io.write(s .. ' ') end 67 | colours = {red=1, yellow=1, pink=1, green=1, orange=1, blue=1, gray=1} 68 | for x in wiki:gmatch('%w+') do 69 | if colours[x] then 70 | print[x](x) 71 | else 72 | print(x) 73 | end 74 | end 75 | 76 | print('\n\n') 77 | 78 | --Now, it's time for some rainbows () 79 | oldprint = print.print 80 | print.print = io.write 81 | 82 | for i = 1, 79 do 83 | print.highlight[( 84 | {'red', 'yellow', 'pink', 'green', 85 | 'orange','blue', 'gray', 'purple'} 86 | )[1 + math.floor(math.abs(math.random()) * 6)]](" ") 87 | end 88 | print('\n') 89 | ``` 90 | 91 | The above code will output something like the following on an ANSI 92 | compatible terminal: 93 | 94 | ![ScreenShot](/img/example_output.png) 95 | -------------------------------------------------------------------------------- /chroma.lua: -------------------------------------------------------------------------------- 1 | return setmetatable({ 2 | escapes = { 3 | red = "\027[31m", 4 | green = "\027[32m", 5 | orange = "\027[33m", 6 | navy = "\027[34m", 7 | magenta = "\027[35m", 8 | cyan = "\027[36m", 9 | gray = "\027[90m", 10 | grey = "\027[90m", 11 | light_gray = "\027[37m", 12 | light_grey = "\027[37m", 13 | peach = "\027[91m", 14 | light_green = "\027[92m", 15 | yellow = "\027[93m", 16 | blue = "\027[94m", 17 | pink = "\027[95m", 18 | baby_blue = "\027[96m", 19 | 20 | highlight = { 21 | red = "\027[41m", 22 | green = "\027[42m", 23 | orange = "\027[43m", 24 | navy = "\027[44m", 25 | magenta = "\027[45m", 26 | cyan = "\027[46m", 27 | gray = "\027[47m", 28 | grey = "\027[47m", 29 | light_gray = "\027[100m", 30 | light_grey = "\027[100m", 31 | peach = "\027[101m", 32 | light_green = "\027[102m", 33 | yellow = "\027[103m", 34 | blue = "\027[104m", 35 | pink = "\027[105m", 36 | baby_blue = "\027[106m", 37 | }, 38 | 39 | strikethrough = "\027[9m", 40 | underline = "\027[4m", 41 | bold = "\027[1m", 42 | }, 43 | _sequence = '', 44 | _highlight = false, 45 | --[[ In the case that the user later overrides `print` or sets `print` to 46 | this table we save it for internal use 47 | ]] 48 | print = print, 49 | reset_global = function(self) 50 | _G.print = self.print 51 | end 52 | }, 53 | { 54 | __call = function(self, ...) return self.print(...) end, 55 | 56 | __index = function(self, index) 57 | local esc = ( 58 | self._highlight 59 | and rawget(self, 'escapes').highlight[index] 60 | or rawget(self, 'escapes')[index] 61 | ) 62 | local clear = "\027[0m" 63 | local root_table = self 64 | self._highlight = index == 'highlight' 65 | if esc ~= nil then 66 | if type(esc) == 'string' then 67 | self._sequence = self._sequence .. esc 68 | end 69 | return setmetatable({}, { 70 | __call = function(proxy, ...) 71 | _ = self._sequence and io.write(self._sequence) 72 | root_table.print(...) 73 | root_table._sequence = '' 74 | io.write(clear) 75 | end, 76 | __index = function(proxy, k) 77 | return root_table[k] 78 | end, 79 | }) 80 | else 81 | return rawget(self, index) 82 | end 83 | end, 84 | }) 85 | 86 | -------------------------------------------------------------------------------- /img/example_output.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ldrumm/lua-chroma/b9c9440057bb93c021a1ebb70ce1f9994ae624d8/img/example_output.png --------------------------------------------------------------------------------