document.getElementById
、$("#id")
または他のDOMメソッド/ jQueryセレクターが要素を見つけられない理由として考えられるものは何ですか?
問題の例は次のとおりです。
.val()
、.html()
、.text()
)を返しますundefined
null
いくつかのエラーのいずれかが発生する標準のDOMメソッドが返されます。Uncaught TypeError:nullのプロパティ '...'を設定できませんUncaughtTypeError:nullのプロパティ '...'を読み取れません
最も一般的な形式は次のとおりです。
Uncaught TypeError:nullのプロパティ 'onclick'を設定できません
Uncaught TypeError:nullのプロパティ 'addEventListener'を読み取れません
Uncaught TypeError:nullのプロパティ 'style'を読み取れません
スクリプトの実行時に、検索しようとした要素がDOMにありませんでした。
DOMに依存するスクリプトの位置は、その動作に大きな影響を与える可能性があります。ブラウザはHTMLドキュメントを上から下に解析します。要素はDOMに追加され、スクリプトは(通常)検出されたときに実行されます。これは、順序が重要であることを意味します。通常、スクリプトは、マークアップの後半に表示される要素を見つけることができません。これらの要素はまだDOMに追加されていないためです。
次のマークアップを検討してください。スクリプト#1は<div>
、スクリプト#2が成功している間、検索に失敗します。
<script>
console.log("script #1: %o", document.getElementById("test")); // null
</script>
<div id="test">test div</div>
<script>
console.log("script #2: %o", document.getElementById("test")); // <div id="test" ...
</script>
それで、あなたは何をすべきですか?いくつかのオプションがあります。
スクリプトをページのさらに下、body終了タグの直前に移動します。このように編成されているため、スクリプトが実行される前に、ドキュメントの残りの部分が解析されます。
<body>
<button id="test">click me</button>
<script>
document.getElementById("test").addEventListener("click", function() {
console.log("clicked: %o", this);
});
</script>
</body><!-- closing body tag -->
注:スクリプトを下部に配置することは、一般的にベストプラクティスと見なされます。
ready()
次を使用して、DOMが完全に解析されるまでスクリプトを延期します。$(handler)
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script>
$(function() {
$("#test").click(function() {
console.log("clicked: %o", this);
});
});
</script>
<button id="test">click me</button>
注:単純に結合することができるDOMContentLoaded
か が、それぞれがその警告を持っています。jQueryはハイブリッドソリューションを提供します。window.onload
ready()
委任されたイベントには、後でドキュメントに追加される子孫要素からのイベントを処理できるという利点があります。
要素がイベントを発生させると(それがバブリングイベントであり、その伝播を停止するものがない場合)、その要素の祖先の各親もイベントを受け取ります。これにより、ハンドラーを既存の要素にアタッチし、イベントが子孫からバブルアップするときにイベントをサンプリングできます...ハンドラーがアタッチされた後に追加されたものも含まれます。イベントをチェックして、目的の要素によって発生したかどうかを確認し、発生した場合はコードを実行するだけです。
jQueryon()
はそのロジックを実行してくれます。イベント名、目的の子孫のセレクター、およびイベントハンドラーを提供するだけです。
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script>
$(document).on("click", "#test", function(e) {
console.log("clicked: %o", this);
});
</script>
<button id="test">click me</button>
注:通常、このパターンは、ロード時に存在しなかった要素、または大量のハンドラーのアタッチを回避するために予約されています。また、document
(説明のために)ハンドラーをアタッチしましたが、最も近い信頼できる祖先を選択する必要があることも指摘しておく価値があります。
defer
属性のdefer
属性を使用します<script>
。
[
defer
、ブール属性、]は、ドキュメントが解析された後、起動する前にスクリプトが実行されることをブラウザに示すために設定されますDOMContentLoaded
。
<script src="https://gh-canon.github.io/misc-demos/log-test-click.js" defer></script>
<button id="test">click me</button>
参考までに、その外部スクリプトのコードを次に示します。
document.getElementById("test").addEventListener("click", function(e){
console.log("clicked: %o", this);
});
注:defer
属性は、確かにそうです魔法の弾丸のようにしかし、それは点に注意することが重要です...
1.defer
外部スクリプトのみを使用することができ、すなわち:を有するものsrc
の属性を。
2.ブラウザのサポートに注意してください。つまり、IE <10でのバグのある実装
短くて単純:探している要素がドキュメントに(まだ)存在しないためです。
この回答の残りのために私が使用するgetElementById
一例として、しかし同様に当てはまりgetElementsByTagName
、querySelector
選択要素こと、および任意の他のDOM方法。
考えられる理由
要素が存在しない理由は2つあります。
渡されたIDを持つ要素は、実際にはドキュメントに存在しません。渡すgetElementById
IDが(生成された)HTMLの既存の要素のIDと実際に一致していること、およびIDのスペルを間違えていないことを再確認する必要があります(IDでは大文字と小文字が区別されます!)。
ちなみに、実装とメソッドを備えた現代のブラウザの大部分では、CSSスタイルの表記法を使用して、要素をその下で取得する方法とは対照的に、たとえば次のように要素を取得します。最初の文字は必須であり、2番目の文字は要素が取得されないことにつながります。querySelector()
querySelectorAll()
id
document.querySelector('#elementID')
id
document.getElementById('elementID')
#
呼び出した時点では、要素は存在しませんgetElementById
。
後者の場合は非常に一般的です。ブラウザはHTMLを上から下に解析して処理します。つまり、そのDOM要素がHTMLに表示される前に発生するDOM要素の呼び出しはすべて失敗します。
次の例を考えてみましょう。
<script>
var element = document.getElementById('my_element');
</script>
<div id="my_element"></div>
の後にdiv
表示されますscript
。スクリプトが実行された時点では、要素はまだ存在しておらず、getElementById
を返しnull
ます。
jQuery
同じことがjQueryのすべてのセレクターに当てはまります。セレクターのスペルを間違えた場合、または実際に存在する前に要素を選択しようとした場合、jQueryは要素を検出しません。
追加のひねりは、プロトコルなしでスクリプトをロードし、ファイルシステムから実行しているためにjQueryが見つからない場合です。
<script src="//somecdn.somewhere.com/jquery.min.js"></script>
この構文は、スクリプトがプロトコルhttps://のページにHTTPS経由でロードできるようにし、プロトコルhttp://のページにHTTPバージョンをロードできるようにするために使用されます。
ロードを試みたり失敗したりするという不幸な副作用があります file://somecdn.somewhere.com...
ソリューション
を呼び出す前にgetElementById
(またはそのことについては任意のDOMメソッド)、アクセスする要素が存在すること、つまりDOMがロードされていることを確認してください。
これは、対応するDOM要素の後にJavaScriptを配置するだけで確認できます。
<div id="my_element"></div>
<script>
var element = document.getElementById('my_element');
</script>
この場合、終了bodyタグ(</body>
)の直前にコードを配置することもできます(すべてのDOM要素はスクリプトの実行時に使用可能になります)。
他の解決策には、load
[MDN]またはDOMContentLoaded
[MDN]イベントのリッスンが含まれます。このような場合、JavaScriptコードをドキュメントのどこに配置するかは重要ではありません。すべてのDOM処理コードをイベントハンドラーに配置することを忘れないでください。
例:
window.onload = function() {
// process DOM elements here
};
// or
// does not work IE 8 and below
document.addEventListener('DOMContentLoaded', function() {
// process DOM elements here
});
イベント処理とブラウザの違いの詳細については、quirksmode.orgの記事を参照してください。
jQuery
まず、jQueryが正しくロードされていることを確認します。ブラウザの開発者ツールを使用して、jQueryファイルが見つかったかどうかを確認し、見つからなかった場合はURLを修正します(たとえば、最初にhttp:
またはhttps:
スキームを追加したり、パスを調整したりします)。
load
/DOMContentLoaded
イベントをリッスンすることは、jQueryが.ready()
[docs]で行っていることとまったく同じです。DOM要素に影響を与えるすべてのjQueryコードは、そのイベントハンドラー内にある必要があります。
実際、jQueryチュートリアルは明示的に次のように述べています。
jQueryを使用するときに行うほとんどすべてのことは、ドキュメントオブジェクトモデル(DOM)を読み取ったり操作したりするため、DOMの準備ができたらすぐにイベントなどの追加を開始する必要があります。
これを行うために、ドキュメントの準備完了イベントを登録します。
$(document).ready(function() { // do stuff when DOM is ready });
または、簡略構文を使用することもできます。
$(function() {
// do stuff when DOM is ready
});
どちらも同等です。
アクセスしようとしている要素が内にiframe
あり、コンテキスト外でアクセスしようとするiframe
と、失敗する原因にもなります。
iframeで要素を取得したい場合は、ここでその方法を確認できます。
IDベースのセレクターが機能しない理由
ソリューション
宣言後に要素にアクセスするか、次のようなものを使用してみてください $(document).ready();
Ajax応答からの要素に.bind()
は、jQueryのメソッドを使用します。古いバージョンのjQuery.live()
も同じです。
ツール[ブラウザ用のwebdeveloperプラグインなど]を使用して、重複するIDを見つけて削除します。
@FelixKlingが指摘したように、最も可能性の高いシナリオは、探しているノードが(まだ)存在しないことです。
ただし、最近の開発手法では、DocumentFragmentsを使用するか、現在の要素を直接デタッチ/再アタッチするだけで、ドキュメントツリーの外部のドキュメント要素を操作できることがよくあります。このような手法は、JavaScriptテンプレートの一部として、または問題の要素が大幅に変更されている間の過度の再描画/リフロー操作を回避するために使用できます。
同様に、最新のブラウザに展開されている新しい「シャドウDOM」機能を使用すると、要素をドキュメントの一部にすることができますが、document.getElementByIdとそのすべての兄弟メソッド(querySelectorなど)でクエリを実行することはできません。これは、機能をカプセル化し、具体的に非表示にするために行われます。
繰り返しになりますが、探している要素が(まだ)ドキュメントに含まれていない可能性が高いため、Felixが示唆しているように行う必要があります。ただし、要素が(一時的または永続的に)見つからない理由は、それだけではないことにも注意する必要があります。
スクリプトの実行順序が問題ではない場合、問題のもう1つの考えられる原因は、要素が適切に選択されていないことです。
getElementById
渡された文字列はそのままIDである必要があり、それ以外は必要ありません。渡された文字列の前#
に。を付け、IDが。で始まらない場合#
、何も選択されません。
<div id="foo"></div>
// Error, selected element will be null:
document.getElementById('#foo')
// Fix:
document.getElementById('foo')
同様に、の場合getElementsByClassName
、渡された文字列の前に.
:を付けないでください。
<div class="bar"></div>
// Error, selected element will be undefined:
document.getElementsByClassName('.bar')[0]
// Fix:
document.getElementsByClassName('bar')[0]
querySelector、querySelectorAll、およびjQueryを使用して、要素を特定のクラス名と照合.
するには、クラスの直前に配置します。同様に、特定のIDを持つ要素を照合#
するには、IDの直前に置きます。
<div class="baz"></div>
// Error, selected element will be null:
document.querySelector('baz')
$('baz')
// Fix:
document.querySelector('.baz')
$('.baz')
2つ以上の属性(2つのクラス名、またはクラス名とdata-
属性など)を持つ要素を照合するには、各属性のセレクターを、スペースで区切らずにセレクター文字列に並べます(スペースは子孫セレクタ)。たとえば、次を選択します。
<div class="foo bar"></div>
クエリ文字列を使用します.foo.bar
。選ぶ
<div class="foo" data-bar="someData"></div>
クエリ文字列を使用します.foo[data-bar="someData"]
。<span>
以下を選択するには:
<div class="parent">
<span data-username="bob"></span>
</div>
を使用しますdiv.parent > span[data-username="bob"]
。
大文字とスペルは、上記のすべてにとって重要です。大文字と小文字が異なる場合、またはスペルが異なる場合、要素は選択されません。
<div class="result"></div>
// Error, selected element will be null:
document.querySelector('.results')
$('.Result')
// Fix:
document.querySelector('.result')
$('.result')
また、メソッドに適切な大文字とスペルが含まれていることを確認する必要があります。次のいずれかを使用します。
$(selector)
document.querySelector
document.querySelectorAll
document.getElementsByClassName
document.getElementsByTagName
document.getElementById
その他のスペルや大文字の使用は機能しません。たとえば、document.getElementByClassName
はエラーをスローします。
これらのセレクターメソッドに文字列を渡すようにしてください。文字列ではないものを、などに渡すとquerySelector
、getElementById
ほぼ確実に機能しません。
選択する要素のHTML属性が引用符で囲まれている場合、それらは単純な一重引用符(一重引用符または二重引用符)である必要があります。ID、クラス、または属性で選択しようとしている場合‘
、中引用符”
は機能するか、機能しません。
私があなたのコードを試したとき、それはうまくいきました。
イベントが機能していない唯一の理由は、DOMの準備ができておらず、IDが「event-btn」のボタンの準備ができていない可能性があります。そして、JavaScriptが実行され、イベントをその要素にバインドしようとしました。
バインドにDOM要素を使用する前に、その要素の準備ができている必要があります。それを行うには多くのオプションがあります。
オプション1:ドキュメント準備完了イベント内でイベントバインディングコードを移動できます。お気に入り:
document.addEventListener('DOMContentLoaded', (event) => {
//your code to bind the event
});
オプション2:タイムアウトイベントを使用して、バインディングを数秒間遅らせることができます。お気に入り:
setTimeout(function(){
//your code to bind the event
}, 500);
オプション3:JavaScriptインクルードをページの下部に移動します。
これがお役に立てば幸いです。
Reba McEntire が息子の Shelby Blackstock と共有しているクリスマスの伝統について学びましょう。
メーガン・マークルとマライア・キャリーが自然な髪の上でどのように結合したかについて、メーガンの「アーキタイプ」ポッドキャストのエピソードで学びましょう.
ハリー王子が家族、特にチャールズ王とウィリアム王子との関係について望んでいると主張したある情報源を発見してください。
ワイノナ・ジャッドが、母親のナオミ・ジャッドが亡くなってから初めての感謝祭のお祝いを主催しているときに、彼女が今では家長であることをどのように認識したかを学びましょう.
Air travel is far more than getting from point A to point B safely. How much do you know about the million little details that go into flying on airplanes?
The world is a huge place, yet some GeoGuessr players know locations in mere seconds. Are you one of GeoGuessr's gifted elite? Take our quiz to find out!
ランボルギーニの創設者であるフェルッチオランボルギーニが100歳になるのは毎日ではありません(そうです、彼は死んでいて、まだ死んでいると思います。
Appleが自動車分野に参入するという噂はかなり前から渦巻いており、AppleウォッチャーがSixtyEight Researchという会社がAppleの自動車研究開発のシェル会社である可能性が高いと判断したとき、その渦巻きは本当に渦巻いた。また、会社が購入した車は1台だけであることが知られており、その車はAppleが何を考えているかについての手がかりでいっぱいになる可能性があることも伝えています。
太陽系の外側にある架空の大きな物体である惑星Xの探索は、何十年にもわたって人間を魅了してきました。その検索の最新の章は、地球の10倍の大きさで、公転周期が15であるほど遠くにある惑星を指しています。
カムニュートンは昨日、簡単な265ヤードと3回のタッチダウンでファルコンズを引き裂き、別の素晴らしいゲームをしました。その日のハイライトは、上のタッチダウンスローでした。これは、視聴するたびにばかげているだけです。
ロシアのフィギュアスケーター、カミラ・バリエバが関与したドーピング事件が整理されているため、チームは2022年北京冬季オリンピックで獲得したメダルを待っています。
何千人ものAmazonの買い物客がMulberry Silk Pillowcaseを推奨しており、現在販売中. シルクの枕カバーにはいくつかの色があり、髪を柔らかく肌を透明に保ちます。Amazonで最大46%オフになっている間にシルクの枕カバーを購入してください
ラファイエット警察署は、「不審な男性が女性に近づいた」という複数の苦情を受けて、12 月にパデュー大学の教授の捜査を開始しました。
私たちの周りの世界と同じように、言語は常に変化しています。以前の時代では、言語の変化は数年または数十年にわたって発生していましたが、現在では数日または数時間で変化する可能性があります。
認知症を患っている 91 歳のアジア人女性が最近、47 番街のアウター サンセット地区でロメオ ロレンゾ パーハムに襲われました。伝えられるところによると、被害者はサンフランシスコの通りを歩いていたところ、容疑者に近づき、攻撃を受け、暴行を受けました。
“And a river went out of Eden to water the garden, and from thence it was parted and became into four heads” Genesis 2:10. ? The heart is located in the middle of the thoracic cavity, pointing eastward.
人々にチャンスを与えることは、人生で少し遅すぎると私は信じています。寛大に。