過去の桐井戸端BBS (桐ver.9)
26452 テキストボックスに入力された値を検査してNGの場合にはフォーカスが他に動かないようにしたい ABZ研究所 2004/05/25-13:27
フォームにテキストボックスを配置し,これのソースには変数を指定しています。
このテキストボックスに入力された値を検査して,NGの場合にはフォーカスが
他に動かないように制御する定義で悩んでいます。
値の検査の条件は次の通りです。
@未定義か , A文字数 , B数値の範囲 など
テキストボックスのソースが表の[項目]でないので,属性では指定できず,
イベントで処理しようとしています。

テキストボックスがエディタに入っている状態(訂正モードなど)では「入力後」や
「ソース値更新」で何とかなりそうなのですが,やっかいなのがマウスのクリックなど
「表示モード」状態でフォーカスが移動した場合は,「フォーカス喪失」イベント内では
検査してもフォーカスを戻すことは出来ないので,困ってしまいました。
このような処理は,常套手段で何かありそうなのですが,・・・
よろしくお願いいたします。
*win桐9−2004を使用
26453 Re:テキストボックスに入力された値の検査について 宮城 2004/05/25-13:48
記事番号26452へのコメント
ABZ研究所さん、こんにちは。

常套手段は「入力後」ですが、

>やっかいなのがマウスのクリッ
>クなど「表示モード」状態でフォーカスが移動した場合は,「フォーカス喪失」イ
>ベント内では検査してもフォーカスを戻すことは出来ないので,困ってしまいまし
>た。

ここの意味がちょっと・・・。表示モードでフォーカス喪失したとはソース更新が
なかったということでは? それをチェックする狙いはなんですか?

ひょっとして、最初から入っている値でもチェックしようとしているのですか?

26454 Re:テキストボックスに入力された値の検査について ABZ研究所 2004/05/25-14:13
記事番号26453へのコメント
宮城様
常套手段は「入力後」ですが、
>ここの意味がちょっと・・・。表示モードでフォーカス喪失したとはソース更新が
>なかったということでは? それをチェックする狙いはなんですか?
>
>ひょっとして、最初から入っている値でもチェックしようとしているのですか?

はい,その通りです。
具体的には「未定義」を許可していないのですが,新規入力する場合には
当然「未定義」状態なので,入力しない限り他のフォーカスに移動しないようにしたいのです。
実は,フォーカス取得したときに「未定義」だったら「更新モード設定」で「訂正モード」に移行することで,
「入力後」を使えるようにしようとしましたが,これがうまくいきませんでした。

最後の手段は←↓↑→キーをトラップして,未定義をチェックしながらフォーカスを操作するとか考えましたが,
マウスもあるし・・と,悩んでいる次第です。


26455 Re:テキストボックスに入力された値の検査について ONnoji 2004/05/25-14:31
記事番号26452へのコメント
ABZ研究所さん、こんにちは。

<値の検査>
表示モードの場合には、[ソース値取得]メソッドが利用できないでしょうか?
しかし、別の行をクリックされた場合の問題も生じるかもしれませんね。

<フォーカス>

フォーカス設定が禁止されているイベントでは、
当然のことですがフォーカスは移動できません。

こういう場合には、
イベントハンドラでタイマーの実行を予約して
イベントハンドラを終わらせます。

既定のインターバル経過後にタイマーのイベントハンドラが実行されますので、
そこでフォーカスを設定できます。
これはフォーカス設定が禁止されているイベントが終了しているからですけれど…

タイマーの使い方には慣れが必要ですが…

ポイントとしては、
タイマーは必要の無い限り停止していたほうが都合がいいと思います。
タイマーイベントハンドラの冒頭で、タイマーイベント自身の属性をオフにしてしまえば、
一回だけ実行のタイマーになります。

タイマの実行を予約する場合には、
タイマーイベントの属性をオンにすればいいはずです。

一連のイベントハンドラの実行の流れが終了してから、
インターバル経過後に、タイマーイベントハンドラが実行されますよ。

なお、インターバルは百分の1秒単位で設定できますが、
あまり、インターバルを小さくすると問題が起きる処理もあると思います。

インターバルが0秒の時にはタイマーは実行され無かったと思います。

外していたらすいません。

<追伸>

なお、イベントが多重に発生する場合にには、
[トレース出力]ウィンドウでイベントの発生具合を調べることをお勧めします。

実は、作り手側の予想とは違った動作をしている場合があります。
ですから、是非確認されることをお勧めします。

なお、宣伝めいて誠に恐縮ですが、m(__)m
拙作にトレースの結果を見易く整形するアプリがあります。

【多遊】さんのところの140番です。

http://mokuchan.hp.infoseek.co.jp/download/dl-list.htm

失礼しました。m(__)m


26456 Re:テキストボックスに入力された値の検査について 宮城 2004/05/25-14:43
記事番号26454へのコメント
すなおにやればこんな感じだと思いますが、これだとどういう不具合がおこったのですか?

手続き定義開始 tなんとか::フォーカス取得(文字列 &喪失オブジェクト名)
   メソッド呼び出し @フォーム.更新モード設定(2)
手続き定義終了

手続き定義開始 tなんとか::入力後(参照 文字列 &編集文字列,長整数 &モード,参照 長整
数 &入力継続)
 ケース開始
  ケース(&編集文字列="")
   メッセージボックス "かんとか"¥
            ,"入力されていません。"¥
            ,アイコン=!
   &入力継続=1
 ケース終了
手続き定義終了

26457 Re:テキストボックスに入力された値の検査について 悲しげ 2004/05/25-16:25
記事番号26454へのコメント
>具体的には「未定義」を許可していないのですが,新規入力する場合には
>当然「未定義」状態なので,入力しない限り他のフォーカスに移動しない
>ようにしたいのです。

例えば、
1.当初は当該テキスト以外の全てのオブジェクトをフォーカス「禁止」とかにしておいてから(ファミリー利用可)
2.当該テキストの「入力後」か「ソース値更新」イベントで値を判断し
3.ここでヌル以外であればオブジェクト操作コマンドで他オブジェクトのフォーカスを「自動」に変更する。
なんてのはどうでしょう?

ただ、疑問なのは、上記で「新規入力する場合には」とあることから、
では新規入力以外と云うのは、どのような場合なのでしょう?
特にソースが変数と云うことであるから、もしレコードの移動があるような時にどうなるのかな?とか。

26458 訂正と補足 悲しげ 2004/05/25-18:31
記事番号26457へのコメント
>1.当初は当該テキスト以外の全てのオブジェクトをフォーカス「禁止」
>とかにしておいてから(ファミリー利用可)

「(ファミリー利用可)」と云うのは、この1.ではなく、3.のオブジェクト操作コマンドに関する追記でした。
追記箇所を間違えました。<(_ _)>

それと、ソースである某変数に値が入っているかどうかと云うことと、新規入力であるかどうかと云うことは、
全く独立しているのではありませんか?
つまり、その変数の値が未定義だったからと云って即ち新規入力であるとは限らないし、
逆に(前回の処理の名残で)たまたまその変数に値が入っていた場合でも新規入力ではないとは限らないような・・・。(?_?)

あるいは、「新規入力」ボタンをクリックすることで、当該某変数をクリア
(ヌルに)してから進める方法も有り得そうですが、だとしたら、わざわざ
当該テキストのソース値がヌルか否かの過程を経由させる必要もなく、
ボタンクリックだけで「新規入力」である旨を判断できるような・・・。
で、複数行が有り得るのなら、当該テキストのソースは、やはり変数ではなくて項目値の方がいいような気がします。

26498 もう少し調査します。ありがとうございました ABZ研究所 2004/05/28-09:28
記事番号26452へのコメント
いろいろとアドバイスありがとうございます。
ちょっと仕事で桐から離れていました。・・

宮城様
>すなおにやればこんな感じだと思いますが、これだとどういう不具合がおこったのですか?
”すなお”にこの通りの定義だったのですがうまく動作しませんでした。
ただ,テストするため,新規に(伝票)フォームを作り,同様にやっとところ問題なく動作しています。
どうやら,ONnoji様のご指摘にもあるように予想していないイベント(発生or順番)や
属性設定が絡んでいて,作成中の処理に問題があるようです。もう少し,時間をかけて調査します。
当面,フォームを閉じる時に入力されたデータをチェックすることで対処しておこうと思っています。

悲しげ様
>ただ、疑問なのは、上記で「新規入力する場合には」とあることから、では新規入力以外
>と云うのは、どのような場合なのでしょう?
>特にソースが変数と云うことであるから、もしレコードの移動があるような時にどうなる
>のかな?
>とか。
確かにおっしゃるとおり,普通はやらないと思います。で,なぜかというと私自身がwin桐を
よく理解していないため,今回はいろいろな仕様上の制約を受けないように,
表を出来る限り基本状態で使用することとしました。
その一つとして,伝票形式フォームでは当たり前の「グループ化」を避けるため,
レコードの共通フィールドを変数に読み込んでテキストボックスで処理し,あとでまた表に書き戻すようにしました。
グループ化は「あれはできる」けど「これはできない」とか,いろいろありそうだったので・・・

>で、複数行が有り得るのなら、当該テキストのソースは、やはり変数ではなくて項目値の
>方がいいような気がします。
今後,もう少し理解できてくれば「普通」にグループ化で対応したいと思います。

ONnoji様
>こういう場合には、イベントハンドラでタイマーの実行を予約してイベントハンドラを終
>わらせます。
なるほど,このような使い方もあるのですね。
ハードウエアを制御するときもタイマーで,「そろそろ入力が安定しただろう」など
「見込み発車」で使用します。
たしかに時間の設定はトライ&エラーですね。

>実は、作り手側の予想とは違った動作をしている場合があります。
特にイベント発生やエラートラップの順番などが絡んだ場合,ハマってしまいます。
これまでは古典的な方法(「確認」コマンドを挿入して,色々な値をダイアログに表示させながら
デバッグする方法)でやってましたが,トレースも勉強します。

皆様ありがとうございました。
26501 Re:[トレース出力]ウィンドウのこと ONnoji 2004/05/28-10:46
記事番号26498へのコメント
ABZ研究所さん、こんにちは。

[確認]コマンドや[メッセージボックス]コマンドを利用して、
デバッグするのは通常の場合問題ありません。

しかし、[マウス○×△]系のイベントではご法度です。
ダイアログボックスを表示してしまうと…
引き続き発生するはずだった[マウス○×△]系のイベントが、
発生しなくなってしまいますから…
気を付けてください。
※[トレース 確認]コマンドも同様です。

>トレースも勉強します。

他の皆様に誤解のないように念のために書きますが、
これは[トレース 確認]コマンドのことではありません。

[トレース出力]ウィンドウのことを差しています。

なお、桐をインストールした時、[トレース出力]ウィンドウは使用しない設定になっています。
[トレース出力]ウィンドウを使用するには、
[環境設定]で[トレース出力ウインドウを使用する]にチェックを付けた後に桐を再起動する必要があります。

■手順
1.[ツール]メニュー → [環境設定]を選びます。
2.[環境設定]の[一括]タブを選びます。
3.[高度な設定]ボタンをクリックします。
4.[トレース出力ウインドウを使用する]をチェックを付けます。

また、[トレース出力]コマンドを利用すると、
[トレース出力]ウィンドウにメッセージを出力することが可能になります。
※あまり便利ではありませんが、役に立つこともあります。(^^ゞ

手前味噌ですが、よろしければ以下をご参照ください。
§9 デバッグ
http://www.geocities.co.jp/SiliconValley-Bay/7565/guide09.htm

<蛇足>

その他に、デバッグ用の変数をソースにしたテキストボックスを用意して、
[変数変更]メソッドを実行して、表示値を更新し(リドロウする)ます。
そうするとフォーム上でデバッグ用の変数の値が確認できるので便利ですよ。

イベントではブレークポイントは利用できませんが、
ブレークポイントに見立てた、中身が nop だけの一般手続きを call すれば、
プログラムの流れがブレークポイントに見立てた所を通過したか否かを、
[トレース出力]ウィンドウで確認することが可能になりますよ

<追伸>

私( ONnoji )の場合、「様」付けで書かれるのはご勘弁願いたいと思っています。
今後は単に ONnojiさん とお書き願えれば幸いです。
よろしくお願いいたします。


26526 タイマー使ってみました ABZ研究所 2004/05/28-23:33
記事番号26501へのコメント
ONnojiさん
タイマーイベントを活用して,でできないはずのフォーカス取得/喪失イベント+フォーカス設定メソッド
を実現しました。ありがとうございました。
これで,色々な制約から解放されそうですが,多用は禁物なのでしょうか?(メモリにゴミが残るような気もします)
同様に,桐ではifのブロックや繰り返しブロックの中から強制的に脱出したりするのは大丈夫な仕様なのでしょうか?
今のところ,問題は発生していませんが,いずれ痛い目に遭うようで・・
ま,とりあえず,ありがとうございました。
26531 Re:タイマー使ってみました ONnoji 2004/05/29-11:01
記事番号26526へのコメント
ABZ研究所さんは No.26526「タイマー使ってみました」で書きました。

ABZ研究所さん、こんにちは。

>タイマーイベントを活用して,でできないはずのフォーカス取得/喪失イベント+フォーカス設定メソッド
>を実現しました。

それはよかったですね。v(^^)v

他の皆様に誤解があるといけないので、
正確には…
出来ないはずのことが出来たわけではなくて、
じっとイベントが終わるのを待っていたから出来たということですね。
嵐(イベントの流れ)が去るのを待ってから、船出(タイマーが起動)したという感じですね。(^^ゞ

>これで,色々な制約から解放されそうですが,多用は禁物なのでしょうか?
>(メモリにゴミが残るような気もします)

私の場合、
必要に応じて、タイマーのインターバルをセットして予約してということを、
割合と良く行いますが、
ガベージになったりとか、困ったことは一回もありませんよ。

ただし、タイマーのインターバルを最小の1/100にすると、
処理が追いつかなくなる問題はあると思います。
危なそうな場合には、実際に試してみてインターバルを決める必要はありますね。

また、桐ver.5 に比べれば変数の領域も増えていますし、
Win桐で困ったことは今のところありません。

>同様に,桐ではifのブロックや繰り返しブロックの中から強制的に脱出したりするのは
>大丈夫な仕様なのでしょうか?
>今のところ,問題は発生していませんが,いずれ痛い目に遭うようで・・

if ... end を抜けるということを良く聞きますが、
私にはこれはまったく理解できません。
ひょっとしてGOTOやRETURNことですかね??

GOTOやRETURNを使わなくても、
Win桐では構造化コマンドが十分揃っていますから、
GOTOやRETURNの必要性はまったく無いと思っています。
※私は桐ver.5 の時にもGOTOや途中でRETURNは一切使いませんでした。
※残念ながら桐ver.5ではプロシージャという概念が明確になっていませんでしたけれど。

繰り返しが[ do until ]型の場合には、
繰り返し終了の直前で if ... 繰り返し中止 ... end で、
繰り返しを脱出しますが、
これは[ do until ]型では普通のことですし、
何の問題もありませんよ。

もちろん、[ do while ]型の繰り返しの場合には、
[繰り返し中止]コマンドは不用なので使いません。
※問題が予見される場合には、
※安全弁用として仕込むことはありますが、あくまでも例外です。(^^ゞ

戻る