JavaScriptをトリガーするリンクがクリックされたときにWebページが上にスクロールしないようにするにはどうすればよいですか?


135

次のようなjQueryまたはJavaScriptイベントに関連付けられたリンクがある場合:

<a href="#">My Link</a>

ページが上にスクロールしないようにするにはどうすればよいですか?アンカーからhref属性を削除すると、ページが一番上までスクロールしませんが、リンクをクリックできないようです。

回答:


197

クリックイベントのデフォルトアクション(リンクターゲットに移動するなど)が発生しないようにする必要があります。

これを行うには2つの方法があります。

オプション1: event.preventDefault()

.preventDefault()ハンドラーに渡されたイベントオブジェクトのメソッドを呼び出します。jQueryを使用してハンドラーをバインドしている場合、そのイベントはのインスタンスでjQuery.Eventあり、jQueryバージョンのになり.preventDefault()ます。を使用addEventListenerしてハンドラーをバインドしている場合、それはEventの生のDOMバージョンになり.preventDefault()ます。どちらの方法でも、必要なことを実行できます。

例:

$('#ma_link').click(function($e) {
    $e.preventDefault();
    doSomething();
});

document.getElementById('#ma_link').addEventListener('click', function (e) {
    e.preventDefault();
    doSomething();
})

オプション2: return false;

jQueryでは

イベントハンドラーからfalseを返すと、自動的にevent.stopPropagation()およびevent.preventDefault()が呼び出されます

したがって、jQueryでは、代わりにこのアプローチを使用して、デフォルトのリンク動作を防ぐことができます。

$('#ma_link').click(function(e) {
     doSomething();
     return false;
});

生のDOMイベントを使用している場合、HTML 5仕様でこの動作が規定されているため、これは最新のブラウザーでも機能します。ただし、古いバージョンの仕様ではそうではなかったため、古いブラウザとの最大の互換性が必要な場合は、.preventDefault()明示的に呼び出す必要があります。仕様の詳細については、event.preventDefault()とfalseを返す(jQueryなし)をご覧ください。


9
クリックハンドラーのアタッチを必要としないソリューション(3年遅れ)を投稿:stackoverflow.com/a/11246131/216941
Matt Crinklaw-Vogt

この場合、Achillesはリンクをクリック可能として表示したいので、href = "#"をまったく使用する必要がないため、これを行っています。詳細については、私の回答を参照してください。
achecopar 2017年

164

あなたの#!代わりにあなたのhrefを設定することができます#

例えば、

<a href="#!">Link</a>

クリックしてもスクロールしません。

注意してください!これにより、クリックされたときにブラウザーの履歴にエントリが追加されます。つまり、リンクをクリックした後、ユーザーの[戻る]ボタンは以前に表示されていたページに移動しません。このため、この.preventDefault()アプローチを使用するか、両方を組み合わせて使用​​することをお勧めします。

これがフィドルの例です(スクロールバーが表示されるまでブラウザを押し下げてください):http ://jsfiddle.net/9dEG7/


仕様オタクの場合-これが機能する理由:

この動作は、フラグメント識別子への移動セクションのHTML5仕様で指定されています。のhrefを持つリンクが"#"ドキュメントを最上部にスクロールさせる理由は、この動作が空のフラグメント識別子を処理する方法として明示的に指定されているためです。

2. fragidが空の文字列の場合、ドキュメントの指定された部分がドキュメントの先頭になります

"#!"代わりにhref ofを使用すると、このルールを回避できるので簡単に機能します。感嘆符に魔法はありません。これは、便利なフラグメント識別子を作成するだけです。これは、典型的なフラグメントとは著しく異なり、ページの要素のidまたはと一致する可能性が低いためnameです。実際、ハッシュの後にはほとんど何でも置くことができます。不十分な唯一の断片は、空の文字列、単語「top」、またはページ上の要素の属性nameまたはid属性と一致する文字列です。

より正確には、次のアルゴリズムのステップ8に進み、フラグメントの指定された部分をドキュメントから特定するフラグメント識別子が必要です。

  1. URLパーサーアルゴリズムをURLに適用し、解析されたURLのフラグメントコンポーネントをfragidにします。

  2. fragidが空の文字列の場合、ドキュメントの指定された部分がドキュメントの先頭になります。ここでアルゴリズムを停止します。

  3. してみましょうfragid bytesパーセント復号化の結果ですfragid

  4. decoded fragidでは、UTF-8デコーダアルゴリズムをに適用した結果を見てみましょうfragid bytes。UTF-8デコーダーがデコーダーエラーを出力する場合、デコーダーを中止し、代わりにのラベルが付いたステップにジャンプしno decoded fragidます。

  5. DOMに完全に等しいIDを持つ要素がある場合decoded fragid、ツリー順で最初のそのような要素はドキュメントの指定された部分です。ここでアルゴリズムを停止します。

  6. デコードされたフラグメントはありません:DOM内に、値がfragidnotdecoded fragid)と完全に等しいname属性を持つa要素がある場合、ツリー順で最初のそのような要素はドキュメントの指定された部分です。ここでアルゴリズムを停止します。

  7. 場合fragidは、文字列のASCII大文字と小文字を区別しない一致するtop、文書の指示された部分は、ドキュメントのトップです。ここでアルゴリズムを停止します。

  8. それ以外の場合、ドキュメントの指定された部分はありません。

手順8に達し、ドキュメントに示された部分がない限り、次のルールが適用されます。

指定された部分がない場合...ユーザーエージェントは何もしなければなりません。

これがブラウザがスクロールしない理由です。


4
「!」を入れてもかまいません または、IDがDOMの一部でない限り、その他の値。
Gopinath 2013

3
一度この方法の提唱者になった後、私は180を達成し、それに対してアドバイスしました。注意:このようなリンクでもページのURLは変更され、ブラウザの履歴に余分なエントリが追加され、「戻る」ボタンがユーザーの期待する代わりにURLからフラグメントを削除するだけになります。したがって、このソリューション自体は、質問に答える一方で、通常preventDefault()、クリックハンドラーでの使用に代わる望ましい選択肢ではありません-悲しいことに。
Mark Amery 2015

1
href = "javascript :;"を使用しない理由 代わりに?私の知る限り、ブラウザの履歴は変更されません。それについて私の回答に投稿しました。
achecopar 2017年

30

簡単な方法は、このコードを活用することです。

<a href="javascript:void(0);">Link Title</a>

この方法ではページが強制的に更新されることはないため、スクロールバーはそのまま残ります。また、プログラムでonclickイベントを変更し、jQueryを使用してクライアント側のイベントバインディングを処理することもできます。

これらの理由により、上記のソリューションは次の方法より優れています。

<a href="javascript:myClickHandler();">Link Title</a>
<a href="#" onclick="myClickHandler(); return false;">Link Title</a>

myClickHandlerメソッドが失敗しない場合にのみ、最後のソリューションでスクロールジャンプの問題を回避します。


12

呼び出しているコードからfalseを返すことは機能し、さまざまな状況で推奨される方法ですが、これも可能

<a href="javascript:;">Link Title</a>

それがSEOになると、それはあなたのリンクが何のために使われるのかに本当に依存します。他のコンテンツへのリンクに実際に使用する場合は、ここで意味のあるものを使用するのが理想的ですが、リンクを機能目的で使用する場合は、スタックオーバーフローが投稿ツールバーで行うように(太字、斜体、ハイパーリンク)など)、それはおそらく問題ではありません。


9

変更する必要があります

<a href="#">My Link</a>

<a href="javascript:;">My Link</a>

この方法では、リンクをクリックしてもページは上にスクロールしません。これは、href = "#"を使用してデフォルトのイベントが実行されないようにするよりもクリーンです。

呼び出された関数がエラーをスローした場合にが実行されない、または関数にを追加してから使用するのを忘れるなど、この質問に対する最初の回答にこれについての十分な理由がありますreturn false;return false;doSomething()return doSomething();



4

href値を単純に変更できる場合は、以下を使用する必要があります。

<a href="javascript:void(0);">Link Title</a>

私が思いついたもう1つのきちんとした解決策は、jQueryを使用して、クリックアクションの発生を停止し、ページをスクロールさせることですが、href="#"リンクに対してのみです。

<script type="text/javascript">
    /* Stop page jumping when links are pressed */
    $('a[href="#"]').live("click", function(e) {
         return false; // prevent default click action from happening!
         e.preventDefault(); // same thing as above
    });
</script>

確かreturn falseに、preventDefault()行の後になければなりません。そうでなければ、この2行目に到達することはありませんか?
hobailey 2016


2

また、onclick属性内でevent.preventDefaultを使用できます。

<a href="#" onclick="event.preventDefault(); doSmth();">doSmth</a>

エクストラクリックイベントを記述する必要はありません。


0

あなたも単にこのように書くこともできます:-

<a href="#!" onclick="function()">Delete User</a>


0

上部と下部に2つのリンクを含むページを作成します。上部のリンクをクリックすると、ページは下部のリンクが表示されているページの下部までスクロールダウンする必要があります。下部のリンクをクリックすると、ページはページの上部までスクロールする必要があります。



0

CSSを確認してください。この例では、https//css-tricks.com/the-checkbox-hack/がありposition: absolute; top: -9999px;ます。onclick="whatever"クリックされた要素の絶対位置にまだジャンプするため、これはChromeでは特に間抜けです。

を削除するとposition: absolute; top: -9999px;display: none;役立つ場合があります。


0

折りたたみ用のBootstrap 3の場合、アンカーでdata-targetを指定せず、hrefに基づいてターゲットを決定すると、イベントが防止されます。データターゲットを使用する場合は、自分でイベントを防止する必要があります。

<button type="button" class="btn btn-default" data-toggle="collapse" data-target="#demo">Collapse This</button>

<div id="demo" class="collapse"> 
<p>Lorem ipsum dolor sit amet</p>
</div>
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.