アプリ版:「スタンプのみでお礼する」機能のリリースについて

こんにちは。初歩的な質問かもしれませんが、お分かりの方は是非ご教授願います。以前にもロケールとストリングテーブルについてのQAがNo.445463でされていますが、こちらで出された回答と現象が違うかもしれませんので、書いてみました。
<現象>
開発環境上(VisualBasic6.0Enterprise)でストリングテーブルを日本語と英語(U.S.)の2つ設定し、同環境上でロケールを日本語⇔英語切替を行いながらデバッグ実行をしました。その際はロケールに対応したストリングが呼び出され、該当した言語で表現されました。
しかし、実際作成したexeにて同様の実行を行ったところ、必ず日本語のストリングが呼び出されてしまい。英語ロケール時に英語テーブルが呼ばれません。
<OS環境>
コンパイル・実行ともにWindows2000professional(日本語版・ロケールも日本語)です。

No.445463の方の例を忠実に手直ししようと思いましたが、多言語テーブルの場合とちょっと違う気がします。この現象を解決するにはどうすればよろしいのでしょうか?あと、自分の解釈ではロケールとは"地域のオプション"の"全般"タブにあるコンボのことだと思うのですが、他にも設定が必要なんでしょうか?
ご回答、よろしくお願いします。

A 回答 (3件)

文字化けについて、、、



日本OSでリソースから読み取った日本語文字が化けるというのですか?
もしそうなら、、、
リソースから読まずに、固定で画面に文字列をセットしても化けるのですか?
画面でなくて、メッセージボックスで表示しても化けますか?

固定で決めうちした文字列で化けて、メッセージボックスでは化けない場合は、
フォームロード時に、最初にフォームのフォント、次にフォームのコントロール類のフォントを変更してあげたら対応できると思います。
おすすめはMSUゴシック

そうでなければ、化ける場合をパターン別に細かく書いてもらわないと答えようがありません。。。
    • good
    • 0
この回答へのお礼

TAGOSAKU7さん、お忙しいところの即レスにもかかわらずお返事遅くなり申し訳ありません。
文字化けに関してですが、前回教えていただいたロジックを実行したときに起こったことなのですが、「日本語」または「ENGLISH」をストリングテーブルから参照しダイアログで表示するとき、開発環境にてシステムロケール=英語(U.S.)だと「ENGLISH」と表示していたところ、exe実行時に「????」などのように表示されてしまうのです。フォントはダイアログmsgbox関数が持つデフォルトのものであると思われます。英語ストリングが選択されていれば「ENGLISH」と正しく表示されることが然りではないでしょうか?ちなみに他の一部のアプリケーションで同様に「?????」と表示されている個所がありました。ちなみにそのときスタートメニューは日本語で表示されてました(当たり前かも)
また、実はあれからいろいろ調べていくうちに、実行時に得るロケールはexeを実行するOS自身の言語版に深く依存していることが分かりました。具体的なロジックレベルまで理解している訳ではありませんが、各国語版のOSはそれぞれネイティブの言語(UI Languageというらしいです)を内部的に持ち、その言語に基づいてストリングテーブルの選択を行うということのようです。ロジックでこれを書き換えることは不可能(または相当手間がかかる)らしいです。対応としてはMSDN上ではサテライトDLLを各言語毎に作成し、実行環境毎に個別に呼ぶ方法、他にIPDKというツールがあるようですが、現状ではまったく理解できてないのでここで詳しく述べることができません。こういったツールについてご存知でしたらヤブヘビということもありますね・・・

お礼日時:2003/02/06 00:53

調べは限界なので、想像の世界を書き込みます。



SetThreadLocaleは、現在のスレッドに対して、ロケールを設定するようです。OS全体に影響するものではありません。

んで、デバッグ環境とEXEにしてからの実行結果が違う事について、、、
「親」と言う事に注目してみると・・・
※デバッグ環境
   (1)デスクトップ → (2)VB → (3)デバッグ環境で擬似EXE
※EXE
   (1)デスクトップ → (2)EXE
となります。
スレッドと言う概念を元に考えると、デスクトップは親として扱われないので、最上位の親が、デバッグ環境とEXEでは違うことになります。

VB自身が開発ツールであることと、デバッグ環境とEXE環境の実行結果から、私たちの見えないところで、VB自身が[GetUserDefaultLCID][SetThreadLocale]をコールしている事が想像できます。
だからこそEXEにしたら、それらは自身でコールしてあげないといけないのだと思います。
(想像だらけでスマソ)


さらに、、、文字化けですが、、、、
読み込んだ文字をそのままフォームに張って、「文字化けがおきる」と言ってませんか?
ストリングテーブルが英語なら、MSGBOXで表示したらうまくいかないですか?
そこでうまく表示できたなら、ロケール以前にフォントの問題だと思われます。

それと、その現象が起こるということは、ストリングテーブルのロケール反映ができたとして捕らえておきますね。
    • good
    • 0
この回答へのお礼

TAGOSAKU7さん、引続きお付き合い頂き、ありがとうございます。想定とはいえ、処理系作成者(MS)くらいしか核心が分からないことかもしれませんね。実際APIを組み込んでテストしてませんが、現状の知識ではAPIを組み合わせることが最善のようです。しかし、この点についてはMSDNの説明が不十分である可能性もありますので、結論付けは少し時間を頂きたいと思います。後半仰られた文字化けの件ですが、会社PCで再現させたところ(かなり危険かも)原因は日本語の文字コードを変換できなかったために"???"という表示になるようです→前回は言葉が足りませんでした。やはりストリングテーブルのロケール反映は不能でした・・・と、いうことは、手動でのロケール設定は不可能ということかなぁ。それとも英語版OSを用意してテストすべきでしょうかねぇ・・・

お礼日時:2003/01/31 13:34

質問者が履歴で挙げた過去スレに答えていた者です。



前回の質問は、
開発環境:US版OS
実行環境:多国(日本語は含まない)
という状況でした。
悲しい事にそんな環境が手元にあるわけもなく、
「日本語版での環境で、日本語テーブルを含まない、複数のストリングテーブル」
を対象にした方法を述べたつもりです。


今回の場合は、前回の質問とちょっと違います。
「日本語版での環境で、日本語テーブルを含む、複数のストリングテーブル」
です。
そうであれば、特にリソースをスクリプト化する必要もありません。
手元にサンプルがあったのでサンプルを載せておきます。


※注意事項----------非常に大事-----------
デバッグ環境だと、対応しないので、EXEの状態で試してみてください。
※注意事項----------非常に大事-----------

ちなみに
日本語ロケールID:1041
英語USロケールID:1033
です


Project1.vbp(プロジェクト)
├Module1.bas(モジュール)
└Test.res(リソース)

*****Module1.basの内容*****
Option Explicit

Public Declare Function GetUserDefaultLCID Lib "KERNEL32" () As Long
Public Declare Function SetThreadLocale Lib "KERNEL32" (ByVal Locale As Long) As Long
Public Const API_FALSE = &H0&

Sub Main()
  Dim lngNowLCID As Long   '//現在のロケールID
  Dim lngNewLCID As Long   '//入力後のロケールID
  Dim strRet   As String  '//インプットボックス戻り
  
  '地域のオプションでセットされているロケールを取得する
  lngNowLCID = GetUserDefaultLCID
  
  Do
    strRet = InputBox("現在のロケールは[" & lngNowLCID & "]です", _
          "ロケールIDを指定してください。", lngNowLCID)
    
    '数値のみ対応
    If Not IsNumeric(strRet) Then
      Exit Sub
    End If
    lngNewLCID = CLng(strRet)
    
    '取得したロケールを、現在のスレッドにセット
    If API_FALSE = SetThreadLocale(lngNewLCID) Then
      'ロケール設定エラー
      MsgBox "ロケール設定に失敗", vbCritical Or vbOKOnly
    Else
      'リソースを読んで表示
      MsgBox LoadResString(101), vbInformation Or vbOKOnly
    End If
  Loop
  
End Sub

*****Test.resの内容*****
構成:日本語テーブル/英語(U.S.)テーブルの計2つのテーブル
ID:101
内容:日本語テーブル側の文字列="日本語"/英語(U.S.)テーブル側の文字列="English"




それと、、、
>同環境上でロケールを日本語⇔英語切替を行いながらデバッグ実行をしました。
>その際はロケールに対応したストリングが呼び出され、該当した言語で表現されました。
とありますが、おそらくVBは
デバッグでは、GetUserDefaultLCID 関数(コンパネで設定されたロケールID)
EXEでは、GetSystemDefaultLCID 関数(OSが持っているロケールID)
を使用しているからだと、勝手に思っています。(違っていたらゴメソ)
    • good
    • 0
この回答へのお礼

TAGOSAKU7さん、こんにちは。早速教えていただいたソースを試してみました(自宅でですが、同じ環境なのです)。GetUserDefaultLCIDでは正しく地域のオプションで設定したロケールIDを返しますが、実際ストリングテーブルを切り分けるトリガは別のようですね。ひょっとしてTAGOSAKU7さんはGetUserDefaultLCIDで取得したロケールIDをSetThreadLocaleでシステムに対して再度設定する、ということなんでしょうか?両方の関数の機能を考えると何とかなりそうですね?MSDNには「システムのLCIDを基準にして(GetSystemDefaultLCIDのことでしょうか?)、実行時に自動的に選択されます」とありますが、システムロケールを手動変更すると文字化けしてストリングテーブル以前の問題になっちゃうんですよねぇ・・・ともあれ、長文でのご回答、大変感謝いたします。もし追加情報ありましたら、是非お伝えください。

お礼日時:2003/01/30 22:21

お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!