前言
本文是参考Build a Command Line app with Go: lolcat所实现的一个 toy-demo ,主要用于本人的一个留档记录。
开始实践
获取测试文本
这里我们导入syreclabs.com/go/faker
用于获取测试文本,使用如下语句导入:
1
| go get -u syreclabs.com/go/faker
|
该部分代码如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
| package main
import ( "fmt" "strings"
"syreclabs.com/go/faker" )
func main() { var phrases []string
for i := 1; i < 3; i++ { phrases = append(phrases, faker.Hacker().Phrases()...) }
fmt.Println(strings.Join(phrases[:], "; ")) }
|
输出效果如下:
改变输出文本颜色
我们可以通过在输出语句中添加转义字符序列来实现这一点。这里将所有输出的字符串转为金色,其 RGB 颜色代码为 (255,215,0):
代码如下所示:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23
| package main
import ( "fmt" "strings"
"syreclabs.com/go/faker" )
func main() { var phrases []string
for i := 1; i < 3; i++ { phrases = append(phrases, faker.Hacker().Phrases()...) }
output := strings.Join(phrases[:], "; ") r, g, b := 255, 215, 0
for j := 0; j < len(output); j++ { fmt.Printf("\033[38;2;%d;%d;%dm%c\033[0m", r, g, b, output[j]) } }
|
效果图:
实现彩虹输出
接下来我们在金色的基础上,通过调整 RGB 的不同值,去实现彩虹输出,代码如下:
1 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 32
| package main
import ( "fmt" "math" "strings"
"syreclabs.com/go/faker" )
func rgb(i int) (int, int, int) { var f = 0.1 return int(math.Sin(f*float64(i)+0)*127 + 128), int(math.Sin(f*float64(i)+2*math.Pi/3)*127 + 128), int(math.Sin(f*float64(i)+4*math.Pi/3)*127 + 128) }
func main() { var phrases []string
for i := 1; i < 3; i++ { phrases = append(phrases, faker.Hacker().Phrases()...) }
output := strings.Join(phrases[:], "; ")
for j := 0; j < len(output); j++ { r, g, b := rgb(j) fmt.Printf("\033[38;2;%d;%d;%dm%c\033[0m", r, g, b, output[j]) } fmt.Println() }
|
效果图如下:
读取其他程序的输出
在前面的基础上,我们让这个程序不再提供自己的输出,而是作为其他程序的管道,它将读取内容 os.Stdin 并将其彩虹化,使其真正成为一个可用的命令行工具。
代码如下:
1 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 32 33 34 35 36 37 38 39 40 41 42 43 44 45
| package main
import ( "bufio" "fmt" "io" "math" "os" )
func main() { info, _ := os.Stdin.Stat() var output []rune
if info.Mode()&os.ModeCharDevice != 0 { fmt.Println("The command is intended to work with pipes.") fmt.Println("Usage: fortune | gorainbow") }
reader := bufio.NewReader(os.Stdin) for { input, _, err := reader.ReadRune() if err != nil && err == io.EOF { break } output = append(output, input) }
print(output) }
func rgb(i int) (int, int, int) { var f = 0.1 return int(math.Sin(f*float64(i)+0)*127 + 128), int(math.Sin(f*float64(i)+2*math.Pi/3)*127 + 128), int(math.Sin(f*float64(i)+4*math.Pi/3)*127 + 128) }
func print(output []rune) { for j := 0; j < len(output); j++ { r, g, b := rgb(j) fmt.Printf("\033[38;2;%d;%d;%dm%c\033[0m", r, g, b, output[j]) } fmt.Println() }
|
效果图如下:
作为命令行工具使用
对项目进行编译后就可以作为一个命令行工具正常使用啦,示例如下: