[CLA-R]列挙体を操作画面に使っていいの?多言語対応について

CLA更新試験(CLA-R)のサンプル問題に次のような問題がありました。

15. Which of the following coding practices is most likely to cause problems for localization of a VI?

a. User-visible panels with enum controls
b. User-visible panels with string controls whose default value is anything other than an empty string
c. User-visible panels using non-system fonts
d. User-visible panels using non-system controls

引用元:Certified LabVIEW Architect (CLA) *サンプル問題のダウンロードにはログインが必要

これは、作ったVIを多言語対応する場合の問題です。多言語対応は制御器のキャプションなどの動的に設定できるようにしたり、キャプションの幅を調整したり、小数点をどう表現するか(日本は.(ピリオド)が小数点なのに対して、欧州では,(カンマ)が小数点の場合がある)だったり、小数点についてはVISA読み書きする場合は国に関係なく.(ピリオド)だったり…すごく面倒です。問題文を日本語にするとこんな感じになると思います。まあ、問題にはこういっためんどくささは関係ないですが。日本語にするとこんな感じです。

15. VIの多言語対応をしようとしたときに一番困りそうなものは次のうちどれですか?

a.
ユーザーが操作する列挙体制御器
b. デフォルト値が空文字ではない文字列制御器
c. システムフォントではないパネル
d.
システムではない制御器

タイトルから推測できると思いますが、答えは

A:User-visible panels with enum controls

です。しかし、なぜ画面に列挙体を使うのが多言語対応に望ましくないのでしょうか?ここではそれについて記述します。

なぜ列挙体が答えなのか?

列挙体とテキストリングの違い

まず、列挙体とは

  • 文字列を数値で表現したもの

です。つまり、人が見たら文字列で、プログラム的には数値として扱うというものです。文字列を数値として取り扱うことで、人には理解しやすく、プログラムにとってはメモリ使用量を少なく(あるいは固定に)できます。また、列挙体を使うことでタイプミスのリスクを減らすことができます。

これだけならテキストリングと同じです。テキストリングとの違いは何でしょうか?このブロックダイアグラムがその違いを表します。

上が列挙体。下がテキストリング

列挙体のケースストラクチャ(上)では文字列”あ”がケースセレクタに表示していますが、テキストリング(下)ではケースセレクタに数値(0)が表示されています。これは、テキストリングはブロックダイアグラムでは数値としてしか扱っていないのに対して、列挙体では文字列情報も静的に持っているということを示します。文字列をフォーマット関数を使っても、両者の違いが分かります。

列挙体とテキストリングに対して文字列をフォーマット

列挙体のほうは表示されている文字列になっているのに対し、テキストリングではその内部の数値になっています。文字列をブロックダイアグラム上にデータとして持っているかというのが両者の違いと言えます。…まあ、テキストリングでもプロパティで文字列をとってこれますが。いや、プロパティでとってくるからUIスレッドから取ってくるのか?…よく分からないです。

列挙体を画面に使うとどうなるか

ここまでの作文で列挙体とテキストリングの違いが分かったかと思います。…というほど分かりやすい説明ができたかは謎です。まあ、列挙体がデータとして文字列を持つということは、実行中にこの文字列を変えられないということです。

プロパティ:String[]で文字列を変えようとした結果

プロパティ:String[]は列挙体もテキストリングも持っていますが、列挙体ではこれを実行中に変更することができません。もし実行中に変更で来たら、ケースストラクチャのケース名がおかしなことになりますからね。実行中に変えられないということは、次のときに困ります。

これまで日本語で表示してたけど、海外展開で英語対応もしたい

テキストリングなら表示を動的に変えられますが、列挙体で対応することはできません。2つの列挙体の表示器を作って重ねて、選んだ言語によってVisibleプロパティで表示/非表示を設定するという姑息な手段で対応できるかもですが、合理性がないですね。なので、列挙体を画面で使うと多言語対応で困るという結果になり、最初の問題の答えは列挙体になります。

列挙体とテキストリングの型変換の例

列挙体を画面で使うと多言語対応がうまくできないことが分かりました。しかし、多言語対応は画面での話で、内部的な処理まで多言語対応する必要はありません。内部的はテキストリングより列挙体のほうが可読性が高いので、可能なら列挙体を使ったほうがいいと考えています。なので、画面ではテキストリングを使って、すぐに列挙体に変換するのがいいと思います。その変換をする例としてCoerce to Typeがあります。日本語だとタイプに強制変換だったかな?

Coerce to Type

これを使うことで、テキストリングの値に対応する列挙体に変換できます。ただし、これはテキストリングと列挙体の数値と文字列の対応が一致している場合にしか使えません。そうでない場合は…変換するサブVIを自作するしかないですね。

列挙体の選択肢がテキストリングだったら?

ここまでの内容から、列挙体の選択肢がテキストリングだった場合は多言語対応が可能と言えます。テキストリングでは表示する文字列を実行中でも変更できるからです。サンプル問題をベースにしたトラップ問題を作るなら、列挙体をテキストリングに変えるというのが考えられるかもしれません。

ほかの選択肢はどうか?

一応ほかの選択肢も確認していきます。

初期値が空でない文字列

制御器やDefault ValueプロパティやVIのMake Current Defaultメソッドは実行中のVIには使えない(正確には制御器のDefault Valueは実行中ではRead Only)ので、リリースしたアプリケーションの初期値の書き換えには使えません。ですが、プログラム起動時にローカル変数やプロパティ:値などで書き換えることは容易なので、これで実質的に初期値の多言語対応を実現できます。

これで書き込み内容を
多言語対応すればいい

システムフォントではないフォント

フォントはプロパティで変更可能です。

フォントを設定するプロパティ

VI全体のフォントを設定するプロパティやメソッドについては分からなかったので、NIサイトにいるNigelさんに聞いたところ、ないようです(記事作成時点)。私もユーザーが使うことを想定しているプロパティやメソッドの中で探した感じでは見つかりませんでした。

フォントを動的に変更することは難しくないですが、エンドユーザーの環境に設定したフォントが存在することを保証するわけではないです。多言語対応では各国の実行環境にありそうなものを予想するしかないですね。

システム以外の制御器

私の解釈では、これは制御器パレットの”System”を意味すると思っています。

制御器パレットのSystem

これは多言語対応とは関係ないですね。好きなものを使えばいいと思います。この場合のSystemはOS依存というもので、Windowsのバージョン(Windows 10と11など)やmacOSのバージョン(ネコ科の何かの動物)などよって変わることがあります。言語とは関係ありません。まあ、私はSystem制御器を使ったことないですが。

まとめ

今回はCLA-Rの問題の1つである多言語対応と列挙体の関係について紹介しました。列挙体を画面で使うことはあまりおすすめではないということです。じゃあ、ほかの選択肢はどうかと言われると、ソースコードを触らなくてもプログラム的に対応する手段があるというだけで、簡単に対応できるというわけではありません。多言語対応するには各種キャプションやダイアログなどのテーブルを用意し、言語を設定する方法を考え、キャプションの位置や幅などを調整する必要があります。面倒な作業をしないといけません。ちなみに、LabVIEWにはOSの言語設定を取得するプロパティなどはないので、dllなどで問い合わせるかコマンドライン (System Exec.vi) で確認するぐらいしかできないです。

ロケールを取得する例

ここでは、コマンドラインからPowerShellを起動して、Get-Cultureを実行しています。LabVIEWのコマンド実行ではPowerShellに対応していないと思っていましたが、PowerShellを呼び出せばいいのかぁ。実はNigelに聞きました。標準品ではなく特定ユーザーの対応ならファイルに設定を記録するのが楽ですね。いずれにしても、多言語対応はやりたくないですね😊。

タイトルとURLをコピーしました