Go言語(golang)でTUIアプリを作ろう ( その2 TUIライブラリの選択 )

tview採用に至る経過について


まずは、PythonでTUIアプリを作ろう ( その2 TUIライブラリの選択 )同様、ライブラリの選択から始めましょう。


(1) gowid

まず、候補に選定したのが、”gowid”です。その理由は単純です。ドキュメントの冒頭に、

Gowid provides widgets and a framework for making terminal user interfaces. It’s written in Go and inspired by urwid.

とあるように、このツールは、Python urwidに触発されて開発されたものだからです。当然、メソッドの構成なども親和性が高いでしょうから、urwidを知っている人間にとっては、理解しやすいことが予想されます。学習効率を考えれば、gowidに勝るものはないでしょう。

そこで、このgowidをベースにサンプルを書いてみたのですが、「複数画面の遷移処理対応」に問題があり、残念ながら要件を満たせないことが判明しました。画面構成を替えてしまえばよいのですが、前回urwidで開発したアプリケーションとの対比を行いたいので、この部分をサポートできないのは致命的です。
以上のことから、今回の選択対象からは、gowidを外さざる得ない結果となってしまいました。


(2) tview

golangのTUIライブラリでは、最も実績が豊富なものでしょう。ドキュメントを読んだ限りでは、このtviewでは、少なくとも「画面遷移問題」はクリアできそうです。それだけで採用するのは、いささか安易かもしれませんが、選択候補が豊富なわけではないので、無難なこちらで進めることにしてしまいましょう。


日本語対応の検証

とりあえず、これまた必要不可欠な日本語対応だけでもテストしておきます。

下記のプログラムで検証します。
tviewのdemosディレクトリにあるプログラムを持ってきただけですが、最近はUTF-8対応が当たり前になってきたので、日本語入出力もほとんど問題にならなくなってきたのは嬉しい限りです。

//  
// s02_01.go  
//  
  
package main  
import (  
	"github.com/gdamore/tcell/v2"  
	"github.com/rivo/tview"  
)  
func main() {  
	app := tview.NewApplication()  
	inputField := tview.NewInputField().  
		SetLabel("文字を入力: ").  
		SetFieldWidth(10).  
		SetDoneFunc(func(key tcell.Key) {  
			app.Stop()  
		})  
	if err := app.SetRoot(inputField, true).EnableMouse(true).Run(); err != nil {  
		panic(err)  
	}  
}  

入力フィールドをInputFieldで定義、SetLabelメソッドで日本語表示を確認します。次にフィールド入力。矢印キーを動かして、適当な文字を挿入、削除してみましょう。英数、漢字の区別なく正常に処理されていますね。


golangのインストールと開発環境設定

改めて、ここからの「tviewによるTUIアプリケーション開発」に必要な環境と、インストール方法について説明しておきます。

(1) OS

基本的にgolangが動けば良いので、LinuxWindowsMacなどどれでも構いませんが、これ以降、説明するプログラムは特に記述がない限り、Xubuntu20.04で実行しています。ご了承ください。

(2) golangのインストール

ここから、該当のファイルをダウンロードし、適当なディレクトリに展開します。完了後、下記の環境変数を設定します。

GOROOT        golangをインストールしたディレクトリを指定  
PATH          $GOROOT/binを追加  

golangのバージョンですが、今回は下記を使用しました。

$ go version  
go version go1.17.6 linux/amd64  

(3) golangのモジュール環境と開発ディレクトリ

先にgolangを調査した2018年当時は、環境変数 GOPATHに、開発ディレクトリを指定。外部モジュールを含めて、全て$GOPATH/srcに配置されるという形式でした。(これをGOPATHモードと呼ぶらしい。)
しかし、最近では、module-awareモードという形式が推奨されており、GO1.17では、こちらがデフォルトになっています。
選択は、環境変数GO111MODULEで行うようですが、圧倒的にmodule-awareモードのほうがわかりやすいので、こちらを採用します。

以下の手順で、開発ディレクトリを設定します。

1) 適当なモジュール名で初期化 (go mod init
$ go mod init section02  
go: creating new go.mod: module section02  
go: to add module requirements and sums:  
	go mod tidy  

このディレクトリがソースプログラムのディレクトリになります。ここでは、先の”s02_01.go”を配置します。

2) 外部モジュールのインストール (go mod tidy)

プログラム内でimportされている外部モジュールは、”go mod tidy”コマンドでインストールされます。昔のように、go getで指定する必要がなくなっていて、非常に便利ですね。

$ go mod tidy  
go: finding module for package github.com/rivo/tview  
go: finding module for package github.com/gdamore/tcell/v2  
            :  
            :  

これで環境が出来たので、プログラムを実行します。

$ go run s02_01.go  

以上で、簡単な動作確認が出来ました。次回は、「tviewの基本構造」について見ていきましょう。


ソースコードについて

GitHubに登録しました。今回のコードは、Section02となります。