From a2ea8a3e171a9f8d963522f36bf3bce0336348ba Mon Sep 17 00:00:00 2001 From: Alex Date: Sat, 10 Nov 2018 20:39:11 +0300 Subject: [PATCH] Added QR code feature --- ansi.go | 50 ++++++++++++++++++++++++++++++++++++++++++++++++++ app.go | 9 ++++++--- build.sh | 20 ++++++++++++++++++++ sixel.go | 55 +++++++++++++++++++++++++++++++++++++++++++++++++++++++ utils.go | 21 +++++++++++++++++++++ 5 files changed, 152 insertions(+), 3 deletions(-) create mode 100644 ansi.go create mode 100755 build.sh create mode 100644 sixel.go diff --git a/ansi.go b/ansi.go new file mode 100644 index 0000000..3082180 --- /dev/null +++ b/ansi.go @@ -0,0 +1,50 @@ +package main + +import ( + "bufio" + "fmt" + "github.com/mgutz/ansi" + "github.com/qpliu/qrencode-go/qrencode" + "io" +) + +func printAnsiArtQr(w_in io.Writer, grid *qrencode.BitGrid, inverse bool) { + // Buffering required for Windows (go-colorable) support + w := bufio.NewWriterSize(w_in, 1024) + + reset := ansi.ColorCode("reset") + black := ansi.ColorCode(":black") + white := ansi.ColorCode(":white") + + if inverse { + black, white = white, black + } + + height := grid.Height() + width := grid.Width() + line := white + fmt.Sprintf("%*s", width*2+2, "") + reset + "\n" + + fmt.Fprint(w, line) + for y := 0; y < height; y++ { + fmt.Fprint(w, white, " ") + color_prev := white + for x := 0; x < width; x++ { + if grid.Get(x, y) { + if color_prev != black { + fmt.Fprint(w, black) + color_prev = black + } + } else { + if color_prev != white { + fmt.Fprint(w, white) + color_prev = white + } + } + fmt.Fprint(w, " ") + } + fmt.Fprint(w, white, " ", reset, "\n") + w.Flush() + } + fmt.Fprint(w, line) + w.Flush() +} diff --git a/app.go b/app.go index 64fc0a0..431744c 100644 --- a/app.go +++ b/app.go @@ -21,6 +21,7 @@ func main() { address := findLocalIpAddress() randomKey := generateRandomKey(4) + resultLink := "http://" + address + port + "/" + randomKey router.GET("/"+randomKey, func(c *gin.Context) { c.Writer.Header().Set("Content-Type", "text/html") @@ -47,11 +48,13 @@ func main() { } }) - println("Go to http://" + address + port + "/" + randomKey + " to control\n") + printQrCode(resultLink, true) + println("Go to " + resultLink + " to control") + println("Or scan this QR code to open the link on your device") - err := router.Run(port) + errServer := router.Run(port) - if err != nil { + if errServer != nil { killWithMessage("Couldn't start the server, releasing the port, try again") } } diff --git a/build.sh b/build.sh new file mode 100755 index 0000000..6b115a9 --- /dev/null +++ b/build.sh @@ -0,0 +1,20 @@ +#!/usr/bin/env bash + +rm -rf ./dist/ + +go generate +goxc -bc="windows,darwin" -d=./dist + +find ./dist/ -type d -depth -empty -exec rmdir "{}" \; + +if [ ! -d "./dist/" ]; then + echo "Could build nothing" + exit 1 +fi + +echo "Done building, compressing" +cd ./dist/snapshot/ + +for i in */; do + zip -r "${i%/}.zip" "$i"; +done \ No newline at end of file diff --git a/sixel.go b/sixel.go new file mode 100644 index 0000000..88c5da9 --- /dev/null +++ b/sixel.go @@ -0,0 +1,55 @@ +package main + +import ( + "fmt" + "github.com/qpliu/qrencode-go/qrencode" + "io" +) + +func printSixelQr(w io.Writer, grid *qrencode.BitGrid, inverse bool) { + black := "0" + white := "1" + + fmt.Fprint(w, + "\x1BPq\"1;1", + "#", black, ";2;0;0;0", + "#", white, ";2;100;100;100", + ) + + if inverse { + black, white = white, black + } + + height := grid.Height() + width := grid.Width() + line := "#" + white + "!" + fmt.Sprintf("%d", (width+2)*6) + "~" + + fmt.Fprint(w, line, "-") + for y := 0; y < height; y++ { + fmt.Fprint(w, "#", white) + color := white + repeat := 6 + var current string + for x := 0; x < width; x++ { + if grid.Get(x, y) { + current = black + } else { + current = white + } + if current != color { + fmt.Fprint(w, "#", color, "!", repeat, "~") + color = current + repeat = 0 + } + repeat += 6 + } + if color == white { + fmt.Fprintf(w, "#%s!%d~", white, repeat+6) + } else { + fmt.Fprintf(w, "#%s!%d~#%s!6~", color, repeat, white) + } + fmt.Fprint(w, "-") + } + fmt.Fprint(w, line) + fmt.Fprint(w, "\x1B\\") +} diff --git a/utils.go b/utils.go index 051a0df..1dd339d 100644 --- a/utils.go +++ b/utils.go @@ -1,15 +1,36 @@ package main import ( + "github.com/fumiyas/go-tty" "github.com/kardianos/osext" + "github.com/mattn/go-colorable" + "github.com/qpliu/qrencode-go/qrencode" "github.com/russross/blackfriday" "io/ioutil" "math/rand" "net" + "os" "path" "time" ) +func printQrCode(src string, inverse bool) { + grid, errQr := qrencode.Encode(src, qrencode.ECLevelL) + + if errQr != nil { + panic(errQr) + } + + da1, errQrText := tty.GetDeviceAttributes1(os.Stdout) + + if errQrText == nil && da1[tty.DA1_SIXEL] { + printSixelQr(os.Stdout, grid, inverse) + } else { + stdout := colorable.NewColorableStdout() + printAnsiArtQr(stdout, grid, inverse) + } +} + func generateRandomKey(length int) string { letters := []rune("abcdefghijklmnopqrstuvwxyz") sequence := make([]rune, length)