質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

ただいまの
回答率

90.47%

  • JavaScript

    16982questions

    JavaScriptは、プログラミング言語のひとつです。ネットスケープコミュニケーションズで開発されました。 開発当初はLiveScriptと呼ばれていましたが、業務提携していたサン・マイクロシステムズが開発したJavaが脚光を浴びていたことから、JavaScriptと改名されました。 動きのあるWebページを作ることを目的に開発されたもので、主要なWebブラウザのほとんどに搭載されています。

  • jQuery

    6920questions

    jQueryは、JavaScriptライブラリのひとつです。 簡単な記述で、JavaScriptコードを実行できるように設計されています。 2006年1月に、ジョン・レシグが発表しました。 jQueryは独特の記述法を用いており、機能のほとんどは「$関数」や「jQueryオブジェクト」のメソッドとして定義されています。

【javascript】次のイベントに発火しないようにしたい

解決済

回答 4

投稿

  • 評価
  • クリップ 2
  • VIEW 4,168

k499778

score 501

現在HTMLやjavascript,jqueryを使ってボタンクリックイベントを行っています。

バリデーション処理と画面遷移処理を分けねばならず、
イベントの発火順序を生かして
バリデーション処理はmousedownイベント,
画面遷移処理はclickイベント
と切り分けたいと思っています。

そのときなのですが、
バリデーションチェックでエラーがあったら
「指定のclickイベントを発火させない」
といった実装をすることは可能でしょうか?

もし「指定のイベントや次のイベントを発火させない」といった処理の書き方や方法を知っている方がいましたら教えて頂きたいです。
よろしくお願い申し上げます。

  • 気になる質問をクリップする

    クリップした質問は、後からいつでもマイページで確認できます。

    またクリップした質問に回答があった際、通知やメールを受け取ることができます。

    クリップを取り消します

  • 良い質問の評価を上げる

    以下のような質問は評価を上げましょう

    • 質問内容が明確
    • 自分も答えを知りたい
    • 質問者以外のユーザにも役立つ

    評価が高い質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

    質問の評価を上げたことを取り消します

  • 評価を下げられる数の上限に達しました

    評価を下げることができません

    • 1日5回まで評価を下げられます
    • 1日に1ユーザに対して2回まで評価を下げられます

    質問の評価を下げる

    teratailでは下記のような質問を「具体的に困っていることがない質問」、「サイトポリシーに違反する質問」と定義し、推奨していません。

    • プログラミングに関係のない質問
    • やってほしいことだけを記載した丸投げの質問
    • 問題・課題が含まれていない質問
    • 意図的に内容が抹消された質問
    • 広告と受け取られるような投稿

    評価が下がると、TOPページの「アクティブ」「注目」タブのフィードに表示されにくくなります。

    質問の評価を下げたことを取り消します

    この機能は開放されていません

    評価を下げる条件を満たしてません

    評価を下げる理由を選択してください

    詳細な説明はこちら

    上記に当てはまらず、質問内容が明確になっていない質問には「情報の追加・修正依頼」機能からコメントをしてください。

    質問の評価を下げる機能の利用条件

    この機能を利用するためには、以下の事項を行う必要があります。

回答 4

+3

デフォルトの挙動が設定されているものに関してなら、それを止めることは可能です。
例えば a要素 は指定されているURLに遷移するものですが、以下のようにすることでそのデフォルトの挙動(つまり画面遷移)を止めることができます。

var a = ... // a要素の取得
a.addEventListener('click', function (evt) {
    evt.preventDefault();
}, false);

ただ内容を読んでいると、そもそもバリデーションはクリックのタイミングじゃなくてもいいのかなと思いました。

つまりバリデーションのタイミングを別で持ち、もしバリデーションエラーであるならボタンなりリンクなりをそもそも無効にしてしまう、という処理のほうが適切ではないかなと感じましたがいかがでしょうか。

投稿

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2016/04/01 00:14

    回答有り難うございます。
    この投稿は実は以下リンクの続きであり、
    https://teratail.com/questions/31090
    エラーチェックはblurとfocusoutがFirefoxだと使えないため、
    フォーカスアウトを断念しました。
    そこで選択肢として残ったボタン押下時にバリデーションチェックを行っています。

    なのでできればボタン押下時に処理をするのが好ましいと思っていました。

    キャンセル

+2

DOMのEventについては発火を止める事は基本的には出来ません
(input系のタグであればdisable属性を設定することで発生そのものを抑止できますが、完全に非活性になってしまうので今回の要件では適切ではなさそうです)

今回の要件としてはユーザが指定のDOMをclickした時に以下のような動作にしたいのだと思います。

  1. バリデーションチェックを実施
  2. エラーがなければ画面遷移をする

この想定であれば、そもそも1と2の処理をmousedown,clickの2つのイベントに振り分ける必要はあまり無く、単純にclickのイベントハンドラに渡すfunction内部で1の実行結果を元に処理を分岐させれば良いと思います。

バリデーションエラーが発生すれば単純に return でfunctionの処理を終了させてしまえばブラウザ上では何も起こりませんので。

投稿

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2016/04/01 00:19 編集

    回答有り難うございます。

    基本的に無理なのですか。

    そうなんですよね。仰るとおり
    最初は同じファンクション内で「バリデーション」と「画面遷移」を行っていて
    エラーだったらreturn falseでファンクションを抜け、画面遷移を行わないようにしていました。

    しかし、画面遷移のファンクションは共通のjsを使っており、
    バリデーションは自分の画面独自のものなので、共通処理の中でバリデーションをしないで欲しいと言われてしまいました。
    もちろん条件分岐で「特定のテキストボックスのときのみバリデーションさせる」という処理は入れています。

    その結果、その切り分けを行うのをどうすればいいのかわからず悩み、ここに投稿した次第です。

    キャンセル

  • 2016/04/01 00:44

    >しかし、画面遷移のファンクションは共通のjsを使っており、
    >バリデーションは自分の画面独自のものなので、共通処理の中でバリデーションをしないで>欲しいと言われてしまいました。

    業務あるあるですね…w
    そのようなケースの場合、以下のように画面遷移の共通処理をもう1つfunctionでラップしたものをイベントハンドラに登録するのはどうでしょうか。

    ```js
    targetDOM.addEventListener('click', function (event) {
    event.preventDefault();
    if(hasValidationError()) return;
    moveTo(event); // ここで共通の画面遷移処理を実行する
    });
    ```

    キャンセル

  • 2016/04/01 07:13

    返答ありがとうございます。

    そうですね(^_^;)w

    なるほど。もう一つラップしたものを作って、共通処理にはpreventDefaultで飛ばさないというやり方でしょうか?

    今調べながらなのですが、「moveTo()」はそういったメソッドがあるのでしょうか?
    canvasで使うような、moveTo(x, y)で座標を指定するやり方は見つかったのですがこれは違う気がして。

    あるいは他の回答者様のyamato_hikawaさんのように
    共通jsの関数名を書けばいいのでしょうか?pageJump(); のように。

    もしお時間ございましたらお答えいただけると助かります。


    キャンセル

  • 2016/04/01 12:33

    あぁ、ごめんなさい。 `moveTo` や `hasValidationError` は既存の画面遷移処理メソッドやバリデーションチェック処理に対して便宜的に仮の名前として付けたものです。

    実際にはそこを置き換えてもらう意図でした。

    なんにせよ、解決できたようで幸いです。

    キャンセル

checkベストアンサー

+1

共通処理の中でバリデーションをしないで欲しいと言われてしまいました。

こういうのならいいのでしょうか

// A バリデーション
$("button").on("click", function(eve){
    // バリデーション
    if(!$("form").get(0).checkValidity()){
        eve.stopImmediatePropagation()
    }
})

// B 共通jsのコード
$("button").on("click", function(){
    // 画面遷移
})

A を B より先に登録しておきます
A でバリデーションが失敗したら stopImmediatePropagation を実行して B を実行しないようにします

投稿

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2016/04/01 07:01

    ryls-nmmさん
    回答ありがとうございます。
    このやり方なら期待通りの実装を実現できるかもしれません。
    本日実際に試してみます。
    本当に有難うございます。

    キャンセル

  • 2016/04/01 07:41 編集

    今自分で教えていただいたやり方を実現する簡単なコードを書いてみました。

    登録順が大事だということで、独自処理を共通jsより上に書いたつもりなのですが、共通jsのイベントが先に呼ばれてしまいます。

    この書き方に間違いがあれば教えていただければと思います。

    common.jsの呼び出し位置を下にすることで登録順を変えれると自分は思っています。。


    -----
    ○html側
    ....
    <input type="button" id="hogeBtn">
    </body>
    <script>
    $(function(){

    $('#hogeBtn').on('click', function(eve){
    console.log('独自js');

    if(true){
    eve.stopImmediatePropagation()
    }
    });
    });
    </script>
    <script src="common.js"></script>
    </html>


    ○common.js
    $('#hogeBtn').on('click', function(){
    console.log('共通js');
    });

    ------

    キャンセル

  • 2016/04/01 07:56

    HTMLの方は$(function(){})で書いているのに、common.jsの方は$(function(){})で書かず、インラインのタイミングで呼ばれているからですね。(^_^;)
    $(function(){})だとすべてのDOMを読み込んでから実行されるからインラインより遅いので。

    HTML側をインラインにするか、common.jsを$(function(){})にするかで解決できました。
    失礼しました。

    キャンセル

  • 2016/04/01 12:08

    このやり方でできました!
    ありがとうございます。

    キャンセル

+1

理解できた範囲で書きますが、コードを見せていただいた方が具体的なアドバイスがしやすいです。

共通処理の設定がもし、下記のように書かれていたらダメなんですが、
そうではなく、処理を別関数に任せる形であれば、処理を再利用するのは簡単です。

// 再利用しにくい
$btn.on('click', function(){
  var hoge;
  hoge = .... 
});

別関数に任せるパターン。

// 再利用しやすいパターン

// 遷移処理が関数化されている
var pageJump = function(){
  var hoge;
  hoge = ...
};

$btn.on('click', function(){
  pageJump(); // イベント時には関数実行のみ
});

もし、具体的な処理を別関数に任せているのであれば、.off()を使って共通のクリックイベントを無効にしつつ、中の関数だけ再利用できます。
下記の設定を書くのはバリデートの設定を書いているJSの方です。

// 共通のクリックイベント(ページ遷移)を一旦無効にする。
$btn.off('click');

$btn.on('click', function(){
  // ここでバリデートの処理・関数実行。

  if(エラーがなければ){
    pageJump(); // ページ遷移の処理実行(ページ遷移の関数の再利用)
  }
});

イベントに名前を付けておくと「そのボタンに関連付けられたクリックイベント全て」ではなく、
「そのボタンに関連付けられたページ遷移のイベントだけ」をピンポイントで無効にもできます。

投稿

編集

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2016/04/01 06:57

    yamato_hikawaさん
    回答ありがとうございます。

    今回関数化されており、再利用しやすいパターンだと認識していますので
    アドバイス頂いた形が使えると思います。

    実際今日この知識を武器に勝負してきます。ありがとうございます。

    キャンセル

  • 2016/04/01 09:12 編集

    少し気になったのですが、
    共通jsのoffにしたイベントは他の処理でも使うので、
    offにしたままではいけないような気がしてるのですが、
    その場合もう一度onにする必要があるでしょうか?

    ---

    追記

    でも「特定のid」のクリックイベントを削除して、新たに登録しなおす訳だから他の同じ関数を使うクリックイベントには影響しないかもしれませんね。
    変なこと言ってしまいました。m(__)m

    キャンセル

  • 2016/04/01 11:25

    上の例ですと、特定のボタンのイベントを消すことになるので、
    他のIDが設定されたボタンのイベントについてはそのままです。
    実際に書いて確認された方が良いと思います。

    キャンセル

  • 2016/04/01 12:15

    返答ありがとうございます。
    実際に家でコード作って試してできて、通勤中に思い立ち試すことができませんでした。

    実際のコードは、共通jsの画面遷移処理がクラス名に対して行われていたため、offすることができませんでした。
    offすると他のところの画面処理もできなくなるため。

    ただこのやり方は非常に参考になりました。本当にありがとうございます。

    キャンセル

  • 2016/04/01 16:32 編集

    今回のボタンに対して、独自のクラス名を付けて、それをOFFにするだけでいいと思うのですが…

    共通の処理が↓だとすると、
    $('.common-btn').on(’click’,function(){ ...});

    今回のボタンにはこの共通クラスに加えて、別のIDやクラスを付けて、
    <a class="common-btn original-btn"></a>
    などとします。

    その上で、下記のようにすれば問題ないと思いますがいかがでしょうか?
    var $btn = $('.original-btn');

    $btn.off('click');

    キャンセル

  • 2016/04/02 06:53 編集

    返答ありがとうございます。

    自分もそのようにクラスではないですけど、idをつけてやったのですがうまくいかなかったんですよね。

    $('.common-btn').on(’click’,function(){ ...});

    <a class="common-btn" id=" original-btn"></a>

    $("#original-btn").off('click');

    $("#original-btn").on('click',function(){
    /*処理*/
    });

    のように。

    うまくいかなかったので、共通イベントが割り当てられているcommon-btnをoffにしないといけないのかと思ってしまい、深掘りしている時間もなかったので違うやり方を検討しました。


    他の原因もあるかもしれないのでまた検証してみます。

    キャンセル

  • 2016/04/02 07:41

    jsファイルの読み込み順はどうなっていますか?
    1. 共通のJS
    2. 今回編集するJS
    の順だと問題ないと思います。
    もし読み込みが逆だと、オフにしてもその後でイベントがオンにされてしまうので効かないと思います。

    キャンセル

関連した質問

同じタグがついた質問を見る

  • JavaScript

    16982questions

    JavaScriptは、プログラミング言語のひとつです。ネットスケープコミュニケーションズで開発されました。 開発当初はLiveScriptと呼ばれていましたが、業務提携していたサン・マイクロシステムズが開発したJavaが脚光を浴びていたことから、JavaScriptと改名されました。 動きのあるWebページを作ることを目的に開発されたもので、主要なWebブラウザのほとんどに搭載されています。

  • jQuery

    6920questions

    jQueryは、JavaScriptライブラリのひとつです。 簡単な記述で、JavaScriptコードを実行できるように設計されています。 2006年1月に、ジョン・レシグが発表しました。 jQueryは独特の記述法を用いており、機能のほとんどは「$関数」や「jQueryオブジェクト」のメソッドとして定義されています。