none
buttonコントロールを、複数回連続でクリックした時、キー先読みしたように、イベントが発生してしまう。(Vb2005 windows form) RRS feed

  • 質問

  • (Vb2005 windows form)

    buttonコントロールにおいて、ダブルクリックのようなクリック操作を行った時、クリックイベントが2回発生してしまいます。(1回目のイベントが終了してから、2回目のイベントが発生してしまいます。)

    例えば、

        Private Sub But0102_Click(ByVal sender As System.Object, ByVal e As System.EventArgs)Handles But0102.Click
            Shell("TEST.EXE", AppWinStyle.NormalFocus, True)
        End Sub

    この時、But0102ボタンを素早く2回クリックすると、"TEST.EXE"が実行され、これが終了次第、もう一度"TEST.EXE"が実行されてしまいます。クリックが先読みされてしまうような現象が発生します。これを解消できますでしょうか?

    尚、MSGBOXやダイアログボックス等を表示するコードが含まれる場合、この現象は発生しません。

    よろしくお願いします。

     

    2006年10月13日 16:09

回答

  • 表現悪くてごめんなさい。

    ただしくは、キャッシュ→キュー の事です。

    ”WAIT”なくなっていたのは、私の入力ミスです。

    あわせて、お詫びします。

    みなさまにいただいたご教授、大変参考になりました、以下のコードで解決しました。

           

    コントロールの使用不可では、うまく制御できない場合がありましたので、。RemoveHandlerとAddHandlerを

    使用し、さらにApplication.DoEvents()でshell関数をはさむことにより、確実なものとなりました。

        Private Sub But0101_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles But0101.Click
            RemoveHandler But0101.Click, AddressOf But0101_Click
            Application.DoEvents()  
            Shell("c:\test.exe", AppWinStyle.NormalFocus, True)
            Application.DoEvents()
            AddHandler But0101.Click, AddressOf But0101_Click
        End Sub

    愚問にお付き合いいただき、ありがとうございました。

    それにしても、VB6.0との違いを痛感しております。

    また、よろしくお願いします。

     

    2006年10月15日 4:33

すべての返信

  • こちらが参考になりそうです。

    無効中のボタンをマウスクリックイベントを受けてしまう
    http://forums.microsoft.com/MSDN-JA/ShowPost.aspx?PostID=713489&SiteID=7

    ついでに、

    自分的に目から鱗のコード
    http://blogs.wankuma.com/trapemiya/archive/2006/09/13/38471.aspx

    2006年10月13日 16:16
    モデレータ
  • ごめんなさい、具体的に、次のようなコードでもダメでした。

     Private Sub BUT0101_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles BUT0101.Click
            BUT0101.Enabled = False
            Shell("TEST.EXE", AppWinStyle.NormalFocus, True)
            BUT0101.Enabled = True
            Application.DoEvents()
    End Sub


     

    2006年10月13日 17:40
  • 冷静によ~く確認してみましょう。

    2006年10月13日 18:16
  •  yamashin さんからの引用

    尚、MSGBOXやダイアログボックス等を表示するコードが含まれる場合、この現象は発生しません。

    これは、MSGBOX やダイアログボックスはモーダル表示されているからですね。

    おそらく2回目のクリック時にウィンドウが点滅していると思います。

    さらに続けてボタンをクリックするとわかりやすいでしょう。

    そのときに2回目以降のクリック処理は無効となって完了してしまっているためです。

    2006年10月14日 3:54
  • お世話になります。引き続きですが、

     Private Sub BUT0101_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles BUT0101.Click
            BUT0101.Enabled = False
            Shell("TEST.EXE", AppWinStyle.NormalFocus, True)
            Application.DoEvents() '逆でしたすみません
            BUT0101.Enabled = True  '逆でしたすみません
    End Sub

    VCの場合、Application.DoEvents() でキャッシュされているイベントが開放されるということで、この問題は解決するようですが、VBではうまくいきません。

    よろしくお願いします。


    2006年10月14日 10:20
  •  yamashin さんからの引用

    VCの場合、Application.DoEvents() でキャッシュされているイベントが開放されるということで、この問題は解決するようですが、VBではうまくいきません。

    私の環境(VB2005) ではうまくいきました。

    起動する EXE を "notepad.exe" にして試してみました。

     

    一旦リビルドされてからもう一度試してもだめでしょうか。

     

    2006年10月14日 12:38
  • ダッチ様

    書き込みありがとうございます。 

    私も、メモ帳を起動するようにして試してみました。結果、やはり、ボタンをダブルクリックすると、2つメモ帳が起動されていしまいました。

    ビルド後も同様です。

    コードは以下の通りです。(ボタン名:But0009)

       Private Sub But0009_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles But0009.Click
            But0009.Enabled = False
            Shell("NOTEPAD.EXE")
            Application.DoEvents()
            But0009.Enabled = True

        End Sub

    できれば、ダッチ様うまくいったコードをご教授いただけないでしょうか。

    また、他の手段として、クリックイベントを受け取らない方法等、ありますでしょうか。

    ちなみに、VB6.0の時は、このような現象は発生しませんでした。

    よろしくお願いします。

    2006年10月14日 13:26
  • 頭に RemoveHandler、尾に AddHandler。

    2006年10月14日 13:51
  • じゃんぬねっと様

    ご教授ありがとうございす。RemoveHandler,AddHandler 参考になりました。

    試しましたが、結局クリックイベントがすでに、キャッシュされているのが原因となっているようで、解決にいたっておりません。

    よろしくお願いいたします。

     

    2006年10月14日 14:28
  • なんでいつの間にかWaitなしになってるんでしょう?
    キャッシュされてるって何の話でしょう?

     

    2006年10月14日 16:35
  • 表現悪くてごめんなさい。

    ただしくは、キャッシュ→キュー の事です。

    ”WAIT”なくなっていたのは、私の入力ミスです。

    あわせて、お詫びします。

    みなさまにいただいたご教授、大変参考になりました、以下のコードで解決しました。

           

    コントロールの使用不可では、うまく制御できない場合がありましたので、。RemoveHandlerとAddHandlerを

    使用し、さらにApplication.DoEvents()でshell関数をはさむことにより、確実なものとなりました。

        Private Sub But0101_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles But0101.Click
            RemoveHandler But0101.Click, AddressOf But0101_Click
            Application.DoEvents()  
            Shell("c:\test.exe", AppWinStyle.NormalFocus, True)
            Application.DoEvents()
            AddHandler But0101.Click, AddressOf But0101_Click
        End Sub

    愚問にお付き合いいただき、ありがとうございました。

    それにしても、VB6.0との違いを痛感しております。

    また、よろしくお願いします。

     

    2006年10月15日 4:33
  • すでに解決されているようですが、

     yamashin さんからの引用

    できれば、ダッチ様うまくいったコードをご教授いただけないでしょうか。



        Private Sub But0101_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles But0101.Click
            But0101.Enabled = False
            Shell("notepad.exe", AppWinStyle.NormalFocus, True)
            Application.DoEvents()
            But0101.Enabled = True
        End Sub

     

    起動する Exe を "notepad.exe" にしただけです。

    私の場合はこれっで何度やってもメモ帳は一回しか開きません。

    yamashinさんの環境でなぜ複数回起動されてしまうのかがまだ不思議です。

     

     yamashin さんからの引用

    それにしても、VB6.0との違いを痛感しております。

    同じ VB でも Runtime が違うため仕方がないですね。

    この辺は少しずつ検証して違いを見つけていく必要があると思います。

    アップグレードを行っているのであればこういうサイトもありますので参考にしてみてください。

    VB マイグレーション Tips

     

    2006年10月15日 10:20