Linux Red Hat 6.1 を使っています。
cursesライブラリを使用して、linuxconf のようなウィザードを造っています。
半角カナの扱いで今困っています。
mvprintw(10, 16, "aaaaaaaaaaaa");
mvprintw(11, 16, "aaaaaaaaaaaa");
refresh();
[補足]
・上記の mvprintw()関数は、仮想画面に書く関数です。
printf()みたいなものです。
数字は左上を (0,0)原点としたXY座標で、その位置から書かれます。
refresh()関数は仮想画面を物理画面に描画して、目視できるようになります。
・上記では文字化けするといけないので、「a」としています。
「a」:半角カナの「ア」
と解釈してください。
[結果]
上記のように実行すると、2行目の表示がおかしくなります。
2行目は (11, 16) から書き出す要求をしているにもかかわらず、行頭からの
表示となってしまいます。
---------------aaaaaaaaaaaa
aaaaaaaaaaaa
「-」は空白です。
kterm 上でいろいろ試したところ、なぜか kterm のライン数を大きくすると
この現象が回避されました。
因果関係は全くわからず、また、ライン数を大きくする以外の回避策も
見つからず困っています。
<追加情報です>
ktermのライン数は同じのまま、Y座標を変えて、(10, 15), (11, 15) と
したところ正常に表示されました。
Y座標が「15以下」だと正常に表示されるみたいです。
ますます原因がわからない。。。
識者の方、ご教授願います。
No.2ベストアンサー
- 回答日時:
OKとなる場合、「ア」の行を書いたあと、「イ」を書く座標を明
示的に指定してジャンプしているので、問題なく表示されています。
これに対して、NGとなる場合、「ア」を10個書いたあと、1行下
に移動("LF" = 0A)し、20桁左に移動("ESC [ 2 0 D" = 1B 5B 32
30 44)しています。
半角カナを10個書いて20桁左に行くので、戻りすぎてしまい、表示
がおかしくなるようです。curses が、半角カナが1桁分の幅しかな
いことを認識していないということですね。
なぜ、kterm の大きさや座標の微妙な差で、結果に違いがあるのか
というと、curses は、同じ表示になるなら、なるべく短い出力を
出すように工夫するからです。ちょっとした出力文字数の差で、違
うやり方を選択するので、偶然うまく行ったりいかなかったりする
わけです。(もっとも、本当に最適かどうかはわかりません。この
例では、どの場合でも、直接座標を指定するのは文字数的に損して
る気がします。)
linux の JE というパッケージに、日本語化された pcurses とい
うのが入っているらしいですが、詳しくは知りません。日本語化さ
れたといっても、半角カナが扱えない可能性も高いです。
もし、これを入れてみてもだめなら、半角カナにはこだわらない方
がいいかと思います。あるいは、curses をやめて、termcap を直
接いじるかですね。
この回答への補足
punchan_jp さん、解析、アドバイスありがとうございました。
とても参考になりました。
原因がわからなかったためモヤモヤしていましたが、原因がわかって
すっきりしました。
私の方もいろいろ試したところ、なんとか回避できそうです。
curses が明示的に座標にジャンプする/しないの条件はわからないのですが、
行の最後で改行コードを入れるとOKみたいです。
実際のコードでは、半角カナのデータを仮想画面に書いた後
mvprintw(x, (COLS - 1), "\n");
としました。
で、refresh() 関数で物理画面に描画すれば乱れませんでした。
ただし、半角カナのデータの最後に「\n」を付加した場合は駄目でした。
あと、refresh() 前に move() 関数でカーソル移動させるとカーソル位置が
乱れてしまいました。
カーソル移動は物理描画後にしました。
UNIX、Linux では半角カナを使わないのがいいんですが、どうしても
使わなきゃいけなかったので苦労しました。。。
本当にご協力ありがとうございました。
感謝します。
No.1
- 回答日時:
半角カナでなく、ASCII 文字なら問題ないのでしょうか?
出力する文字コードと kterm の文字コードの設定として
何を使っているでしょうか?
EUC を使っているとすると、半角カナは2バイトで表現されますから、
ちゃんと日本語化された curses でないと正しく扱えないかもしれません。
あとは、kterm のバグが考えられますが、この場合、script コマンドによって
curses がどのような出力をしているかの生の情報を収集できます。
script を起動して、すぐ問題のコマンドを動かし、おかしくなっ
た時点ですぐ終了させて、script も exit で抜けておきます。
そうすれば、typescript というファイルに、それまでに出力され
たバイト列が生成されます。これを適当な方法で解析してください。
うまくいく場合といかない場合の両方を調べて比較するといいかもしれません。
このファイルが巨大でなければ、cat -vt してここに掲載してもらえれば、
調べてみますけど。
この回答への補足
punchan_jp さん、回答ありがとうございました。
ご質問に対してお答えします。
#長くなっちゃったけど大丈夫かなぁ。。。
>半角カナでなく、ASCII 文字なら問題ないのでしょうか?
・ASCII 文字、全角文字なら問題ありません。
>出力する文字コードと kterm の文字コードの設定として
>何を使っているでしょうか?
・出力コードはEUCです。
kterm の文字コードの設定というのは、LANG、LC_ALL のことで
いいのでしょうか。
どちらも ja_JP.ujis となっていました。
>EUC を使っているとすると、半角カナは2バイトで表現されますから、
>ちゃんと日本語化された curses でないと正しく扱えないかもしれません。
・データは2バイトですが、1バイト分で表示されています。
ちゃんと日本語化された curses ライブラリかどうか判断することは
できますか?
6.1 でのリンクは以下のようになっていました。
libcurses.so -> libncurses.so
libncurses.so -> libncurses.so.4
libncurses.so.4 -> libncurses.so.4.2
libncurses.so.4.2 : (1999 Sep 24 274985byte)
ちなみに 6.2 でも同じ現象になりました。
実体は libncurses.so.4.0 (2000 Mar 7 262884 byte) でした。
>あとは、kterm のバグが考えられますが、この場合、script コマンドによって
>curses がどのような出力をしているかの生の情報を収集できます。
>script を起動して、すぐ問題のコマンドを動かし、おかしくなっ
>た時点ですぐ終了させて、script も exit で抜けておきます。
>そうすれば、typescript というファイルに、それまでに出力され
>たバイト列が生成されます。これを適当な方法で解析してください。
>うまくいく場合といかない場合の両方を調べて比較するといいかもしれません。
参考までに、簡単なプログラムを以下に載せておきます。
-------------------- ここから --------------------
#include <curses.h>
main()
{
char tbl_1[80];
char tbl_2[80];
int cnt, cnt2;
int mojiCnt = 10;
initscr();
clear();
memset(tbl_1, '\0', 80);
memset(tbl_2, '\0', 80);
for (cnt = 0, cnt2 = 0; cnt < mojiCnt; cnt++) {
tbl_1[cnt2] = 0x8E;
tbl_2[cnt2] = 0x8E;
cnt2++;
tbl_1[cnt2] = 0xB1;
tbl_2[cnt2] = 0xB2;
cnt2++;
}
mvprintw(10, 16, "%s", tbl_1);
mvprintw(11, 16, "%s", tbl_2);
refresh();
endwin();
}
-------------------- ここまで --------------------
質問を出した後、いろいろ試しましたが、以下の条件が影響すると
わかりました。
・書き出すY座標
・表示する文字数
・kterm のライン数
プログラムで、文字数(mojiCnt)、Y座標(mvprintw 関数の第2パラメータ)を
変更したり、kterm のライン数を変えてテストしました。
例えば上記プログラムは、ライン数:24、カラム:80 の kterm で実行すると
NGですが、ライン数を 25 にするとOKでした。
また、ライン数:24、カラム:80 のままで、座標を (10,15) と (11,15) と
したらOKでした。
データ長にも影響しているらしく、各行2文字ずつ表示した場合、Y座標が
2以下ならOKで、3以上がNGでした。
各行3文字の場合は、Y座標が3以下がOKで、4以上だとNGでした。
(ライン数:24、カラム:80)
Windows のマシンから「TeraTerm」というソフトで telnet して試しましたが
同じ現象が発生しました。
この場合は、LANG、ロケールは ja_JP.eucJP です。
なので curses の問題だとは思うのですが、原因が全く推測できません。
>このファイルが巨大でなければ、cat -vt してここに掲載してもらえれば、
>調べてみますけど。
お時間が許されるならば、よろしくお願いします。
以下が cat の結果とダンプデータです。
cat の結果をファイルに落として vi で見たところ、NGとなった (1) の
場合は1行目の表示と2行目の表示のデータの部分は別の行となっていましたが
OKの場合は1行目の表示と2行目の表示のデータの部分は同じ行として
つながっていました。
ダンプデータを見ると確かに (1) は 1行目のデータの後ろに 0x0A の
改行コードがあり、(2)、(3) では0x0A の改行コードがありませんでした。
(1)上記プログラムを実行(ライン数:24、カラム:80)
結果=>NG
<cat -vt データ>
[nabe@upsx3 testkana]$ cat -vt type16-24
M-%M-9M-%M-/M-%M-jM-%M-WM-%M-HM-$M-O Wed Apr 4 15:47:27 2001
M-$M-KM-3M-+M-;M-OM-$M-7M-$M-^M-$M-7M-$M-?[nabe@upsx3 testkana]$ a.out^M
^[7^[[?47h^[[1;24r^[[m^[[4l^[[H^[[2J^[[11;17HM-^NM-1M-^NM-1M-^NM-1M-^NM-1M-^NM-1M-^NM-1M-^NM-1M-^NM-1M-^NM-1M-^NM-1
^[[20DM-^NM-2M-^NM-2M-^NM-2M-^NM-2M-^NM-2M-^NM-2M-^NM-2M-^NM-2M-^NM-2M-^NM-2^[[24;1H^[[2J^[[?47l^[8^M^[[?1l^[>[nabe@upsx3 testkana]$ exit^M
exit^M
M-%M-9M-%M-/M-%M-jM-%M-WM-%M-HM-$M-O Wed Apr 4 15:47:45 2001
M-$M-KM-=M-*M-NM-;M-$M-7M-$M-^M-$M-7M-$M-?[nabe@upsx3 testkana]$
<ダンプデータ>
00000000 A5 B9 A5 AF A5 EA A5 D7 A5 C8 A4 CF 20 57 65 64
00000010 20 41 70 72 20 20 34 20 31 35 3A 34 37 3A 32 37
00000020 20 32 30 30 31 0A 20 A4 CB B3 AB BB CF A4 B7 A4
00000030 DE A4 B7 A4 BF 5B 6E 61 62 65 40 75 70 73 78 33
00000040 20 74 65 73 74 6B 61 6E 61 5D 24 20 61 2E 6F 75
00000050 74 0D 0A 1B 37 1B 5B 3F 34 37 68 1B 5B 31 3B 32
00000060 34 72 1B 5B 6D 1B 5B 34 6C 1B 5B 48 1B 5B 32 4A
00000070 1B 5B 31 31 3B 31 37 48 8E B1 8E B1 8E B1 8E B1
00000080 8E B1 8E B1 8E B1 8E B1 8E B1 8E B1 0A 1B 5B 32
00000090 30 44 8E B2 8E B2 8E B2 8E B2 8E B2 8E B2 8E B2
000000A0 8E B2 8E B2 8E B2 1B 5B 32 34 3B 31 48 1B 5B 32
000000B0 4A 1B 5B 3F 34 37 6C 1B 38 0D 1B 5B 3F 31 6C 1B
000000C0 3E 5B 6E 61 62 65 40 75 70 73 78 33 20 74 65 73
000000D0 74 6B 61 6E 61 5D 24 20 65 78 69 74 0D 0A 65 78
000000E0 69 74 0D 0A 0A A5 B9 A5 AF A5 EA A5 D7 A5 C8 A4
000000F0 CF 20 57 65 64 20 41 70 72 20 20 34 20 31 35 3A
00000100 34 37 3A 34 35 20 32 30 30 31 0A 20 A4 CB BD AA
00000110 CE BB A4 B7 A4 DE A4 B7 A4 BF
(2)上記プログラムを実行(ライン数:25、カラム:80)
結果=>OK
<cat -vt データ>
[nabe@upsx3 testkana]$ cat -vt type16-25
M-%M-9M-%M-/M-%M-jM-%M-WM-%M-HM-$M-O Wed Apr 4 15:49:58 2001
M-$M-KM-3M-+M-;M-OM-$M-7M-$M-^M-$M-7M-$M-?[nabe@upsx3 testkana]$ a.out^M
^[7^[[?47h^[[1;25r^[[m^[[4l^[[H^[[2J^[[11;17HM-^NM-1M-^NM-1M-^NM-1M-^NM-1M-^NM-1M-^NM-1M-^NM-1M-^NM-1M-^NM-1M-^NM-1^[[12;17HM-^NM-2M-^NM-2M-^NM-2M-^NM-2M-^NM-2M-^NM-2M-^NM-2M-^NM-2M-^NM-2M-^NM-2^[[25;1H^[[2J^[[?47l^[8^M^[[?1l^[>[nabe@upsx3testkana]$ exit^M
exit^M
M-%M-9M-%M-/M-%M-jM-%M-WM-%M-HM-$M-O Wed Apr 4 15:50:13 2001
M-$M-KM-=M-*M-NM-;M-$M-7M-$M-^M-$M-7M-$M-?[nabe@upsx3 testkana]$
<ダンプデータ>
00000000 A5 B9 A5 AF A5 EA A5 D7 A5 C8 A4 CF 20 57 65 64
00000010 20 41 70 72 20 20 34 20 31 35 3A 34 39 3A 35 38
00000020 20 32 30 30 31 0A 20 A4 CB B3 AB BB CF A4 B7 A4
00000030 DE A4 B7 A4 BF 5B 6E 61 62 65 40 75 70 73 78 33
00000040 20 74 65 73 74 6B 61 6E 61 5D 24 20 61 2E 6F 75
00000050 74 0D 0A 1B 37 1B 5B 3F 34 37 68 1B 5B 31 3B 32
00000060 35 72 1B 5B 6D 1B 5B 34 6C 1B 5B 48 1B 5B 32 4A
00000070 1B 5B 31 31 3B 31 37 48 8E B1 8E B1 8E B1 8E B1
00000080 8E B1 8E B1 8E B1 8E B1 8E B1 8E B1 1B 5B 31 32
00000090 3B 31 37 48 8E B2 8E B2 8E B2 8E B2 8E B2 8E B2
000000A0 8E B2 8E B2 8E B2 8E B2 1B 5B 32 35 3B 31 48 1B
000000B0 5B 32 4A 1B 5B 3F 34 37 6C 1B 38 0D 1B 5B 3F 31
000000C0 6C 1B 3E 5B 6E 61 62 65 40 75 70 73 78 33 20 74
000000D0 65 73 74 6B 61 6E 61 5D 24 20 65 78 69 74 0D 0A
000000E0 65 78 69 74 0D 0A 0A A5 B9 A5 AF A5 EA A5 D7 A5
000000F0 C8 A4 CF 20 57 65 64 20 41 70 72 20 20 34 20 31
00000100 35 3A 35 30 3A 31 33 20 32 30 30 31 0A 20 A4 CB
00000110 BD AA CE BB A4 B7 A4 DE A4 B7 A4 BF
(3)上記プログラムを (10,15) (11,15) から書き出すように修正して実行
(ライン数:24、カラム:80)
結果=>OK
<cat -vt データ>
[nabe@upsx3 testkana]$ cat -vt type15-24
M-%M-9M-%M-/M-%M-jM-%M-WM-%M-HM-$M-O Wed Apr 4 15:51:54 2001
M-$M-KM-3M-+M-;M-OM-$M-7M-$M-^M-$M-7M-$M-?[nabe@upsx3 testkana]$ a.out^M
^[7^[[?47h^[[1;24r^[[m^[[4l^[[H^[[2J^[[11;16HM-^NM-1M-^NM-1M-^NM-1M-^NM-1M-^NM-1M-^NM-1M-^NM-1M-^NM-1M-^NM-1M-^NM-1^[[12;16HM-^NM-2M-^NM-2M-^NM-2M-^NM-2M-^NM-2M-^NM-2M-^NM-2M-^NM-2M-^NM-2M-^NM-2^[[24;1H^[[2J^[[?47l^[8^M^[[?1l^[>[nabe@upsx3testkana]$ exit^M
exit^M
M-%M-9M-%M-/M-%M-jM-%M-WM-%M-HM-$M-O Wed Apr 4 15:52:05 2001
M-$M-KM-=M-*M-NM-;M-$M-7M-$M-^M-$M-7M-$M-?[nabe@upsx3 testkana]$
<ダンプデータ>
00000000 A5 B9 A5 AF A5 EA A5 D7 A5 C8 A4 CF 20 57 65 64
00000010 20 41 70 72 20 20 34 20 31 35 3A 35 31 3A 35 34
00000020 20 32 30 30 31 0A 20 A4 CB B3 AB BB CF A4 B7 A4
00000030 DE A4 B7 A4 BF 5B 6E 61 62 65 40 75 70 73 78 33
00000040 20 74 65 73 74 6B 61 6E 61 5D 24 20 61 2E 6F 75
00000050 74 0D 0A 1B 37 1B 5B 3F 34 37 68 1B 5B 31 3B 32
00000060 34 72 1B 5B 6D 1B 5B 34 6C 1B 5B 48 1B 5B 32 4A
00000070 1B 5B 31 31 3B 31 36 48 8E B1 8E B1 8E B1 8E B1
00000080 8E B1 8E B1 8E B1 8E B1 8E B1 8E B1 1B 5B 31 32
00000090 3B 31 36 48 8E B2 8E B2 8E B2 8E B2 8E B2 8E B2
000000A0 8E B2 8E B2 8E B2 8E B2 1B 5B 32 34 3B 31 48 1B
000000B0 5B 32 4A 1B 5B 3F 34 37 6C 1B 38 0D 1B 5B 3F 31
000000C0 6C 1B 3E 5B 6E 61 62 65 40 75 70 73 78 33 20 74
000000D0 65 73 74 6B 61 6E 61 5D 24 20 65 78 69 74 0D 0A
000000E0 65 78 69 74 0D 0A 0A A5 B9 A5 AF A5 EA A5 D7 A5
000000F0 C8 A4 CF 20 57 65 64 20 41 70 72 20 20 34 20 31
00000100 35 3A 35 32 3A 30 35 20 32 30 30 31 0A 20 A4 CB
00000110 BD AA CE BB A4 B7 A4 DE A4 B7 A4 BF
以上
お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!
関連するカテゴリからQ&Aを探す
おすすめ情報
- ・漫画をレンタルでお得に読める!
- ・街中で見かけて「グッときた人」の思い出
- ・「一気に最後まで読んだ」本、教えて下さい!
- ・幼稚園時代「何組」でしたか?
- ・激凹みから立ち直る方法
- ・1つだけ過去を変えられるとしたら?
- ・【あるあるbot連動企画】あるあるbotに投稿したけど採用されなかったあるある募集
- ・【あるあるbot連動企画】フォロワー20万人のアカウントであなたのあるあるを披露してみませんか?
- ・映画のエンドロール観る派?観ない派?
- ・海外旅行から帰ってきたら、まず何を食べる?
- ・誕生日にもらった意外なもの
- ・天使と悪魔選手権
- ・ちょっと先の未来クイズ第2問
- ・【大喜利】【投稿~9/7】 ロボットの住む世界で流行ってる罰ゲームとは?
- ・推しミネラルウォーターはありますか?
- ・都道府県穴埋めゲーム
- ・この人頭いいなと思ったエピソード
- ・準・究極の選択
- ・ゆるやかでぃべーと タイムマシンを破壊すべきか。
- ・歩いた自慢大会
- ・許せない心理テスト
- ・字面がカッコいい英単語
- ・これ何て呼びますか Part2
- ・人生で一番思い出に残ってる靴
- ・ゆるやかでぃべーと すべての高校生はアルバイトをするべきだ。
- ・初めて自分の家と他人の家が違う、と意識した時
- ・単二電池
- ・チョコミントアイス
デイリーランキングこのカテゴリの人気デイリーQ&Aランキング
-
マインクラフト(pc版)で座標...
-
グラフの交点の求め方(Excel)
-
直線上にある点の座標の求め方
-
y=x^2の座標をプロットするプロ...
-
任意の座標が、閉図形の内側か...
-
エクセルで回転する座標の出し方
-
ワード上Shapeの位置情報を統一...
-
C言語で制作するピラミッドアー...
-
ピクセルの座標を取得するには
-
エクセルシート上のマウスポイ...
-
Access2000レポートの罫線
-
Tiny Basicでのグラフィック。。
-
VB6のPrinter.ScaleWidth に対...
-
3次元空間上の2つの座標から...
-
∠ABCに内接する円の中心・接点...
-
Pythonの質問です。 input関数...
-
複数コントロール(ラベル)を...
-
VB.netでSTLファイルの分離
-
エクセルである点からの距離で...
-
添削お願いします(C言語)
マンスリーランキングこのカテゴリの人気マンスリーQ&Aランキング
-
グラフの交点の求め方(Excel)
-
マインクラフト(pc版)で座標...
-
以下のプログラムは重心を求め...
-
ダイアログ内コントロールの位...
-
3次元空間上の2つの座標から...
-
エクセルである点からの距離で...
-
エクセルで回転する座標の出し方
-
シーケンサー(PLC?)で制...
-
C言語 配列で座標
-
始点、終点の二つの座標と半径...
-
閉図形の座標の配列が右回りか...
-
一番近い点を見つけたい。
-
ワード上Shapeの位置情報を統一...
-
最小二乗平面
-
多角形の内部かどうか判定する方法
-
タッチパッドのタッチ座標取得
-
Excel VBA で自在に図形を変化...
-
座標を持った平面範囲に座標を...
-
ピクチャボックスの座標取得
-
DirectInputでの現在のマウス座...
おすすめ情報