Edited at

D言語で半角・全角含めた文字幅を取得するeast_asian_width

More than 1 year has passed since last update.


はじめに

昨年のアドベントカレンダーで、d-man{say,think}を開発しました。

ところが全角文字に対応していませんでした。

$ d-mansay D言語くんだよ

_____________________
< D言語くんだよ >
---------------------
\ _ _
\ (_) (_)
/______ \
\ (O(O \/
| | | |
| |_| |
/______/
< >
(_) (_)

そこで今回は全角文字に対応させます。


east_asian_width

文字通りのdubパッケージがあります。

https://code.dlang.org/packages/east_asian_width

READMEから使い方を抜粋します。

import eastasianwidth;

assert(displayWidth("あいうえお") == 10);

// '☆' is Ambiguous character
assert(displayWidth('☆') == 1);
assert(displayWidth('☆', AmbiguousCharWidth.wide) == 2);
assert(displayWidth("☆D言語くん☆") == 11);
assert(displayWidth("☆D言語くん☆", AmbiguousCharWidth.wide) == 13);

assert(eastAsianWidth('A') == EastAsianWidthProperty.F); // Fullwidth
assert(eastAsianWidth('ア') == EastAsianWidthProperty.H); // Halfwidth
assert(eastAsianWidth('ア') == EastAsianWidthProperty.W); // Wide
assert(eastAsianWidth('A') == EastAsianWidthProperty.Na); // Narrow
assert(eastAsianWidth('☆') == EastAsianWidthProperty.A); // Ambiguous
assert(eastAsianWidth('À') == EastAsianWidthProperty.N); // Neutral

displayWidth('☆', AmbiguousCharWidth.wide) を使ってあげれば良さそうです。


Improve d-man{say,think}

というわけで実装しました。

$ d-mansay 新しいD言語くんは日本語が流暢だよ -W 17

___________________
/ 新しいD言語くんは \
\ 日本語が流暢だよ /
-------------------
\ _ _
\ (_) (_)
/______ \
\\(O(O \/
| | | |
| |_| |
/______/
< >
(_) (_)


参考