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

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

新規登録して質問してみよう
ただいま回答率
85.48%
JavaScript

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

HTML

HTMLとは、ウェブ上の文書を記述・作成するためのマークアップ言語のことです。文章の中に記述することで、文書の論理構造などを設定することができます。ハイパーリンクを設定できるハイパーテキストであり、画像・リスト・表などのデータファイルをリンクする情報に結びつけて情報を整理します。現在あるネットワーク上のほとんどのウェブページはHTMLで作成されています。

Q&A

解決済

1回答

4186閲覧

input要素のonclickなどのイベントハンドラからグローバルな関数`list`にアクセスできない件

Lhankor_Mhy

総合スコア36074

JavaScript

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

HTML

HTMLとは、ウェブ上の文書を記述・作成するためのマークアップ言語のことです。文章の中に記述することで、文書の論理構造などを設定することができます。ハイパーリンクを設定できるハイパーテキストであり、画像・リスト・表などのデータファイルをリンクする情報に結びつけて情報を整理します。現在あるネットワーク上のほとんどのウェブページはHTMLで作成されています。

1グッド

1クリップ

投稿2017/02/18 07:27

###前提・実現したいこと
https://jsfiddle.net/rhjfjqj8/
↑上記サンプルなんですが、input要素のイベントハンドラからはlist関数を参照できません。test関数にはアクセスができます。何故なんでしょうか。

###発生している問題・エラーメッセージ
TypeError: list is not a function

###該当のソースコード

HTML

1<a href="#" onclick="list()">list</a> 2<a href="#" onclick="test()">test</a> 3<br> 4<input type="text" onchange="list()" value="list"> 5<input type="text" onchange="test()" value="test"> 6<br> 7<input type="button" onclick="list()" value="list"> 8<input type="button" onclick="test()" value="test"> 9<br> 10<label><input type="checkbox" onclick="list()">list</label> 11<label><input type="checkbox" onclick="test()">test</label> 12<br>

javascript

1function list(){alert('list');} 2function test(){alert('test');}

###試したこと
予約語関連かと思い検索してみましたが、それらしき情報にあたりませんでした。

###補足情報(言語/FW/ツール等のバージョンなど)
OSはWin7です。Chrome、Firefox、IE11で同様の現象が起きることを確認しました。

maki_k👍を押しています

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

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

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

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答1

0

ベストアンサー

原因は、<input onclick="list()"> がinput要素 の list属性 を参照してしまうためです。
HTML Standard / MDN ←(input要素にはlist属性が存在する)
つまり解決方法は

  • <input>が持つプロパティ名と被らないようにonclick="~"を指定する(姑息的)

(ただし後述するようにdocument(場合によっては<form>も)が持つプロパティとも被らないにする必要があります。)

  • [追記] onclick="window.list()"のようにグローバルオブジェクトを経由する(コメントで教えて頂きました)
  • addEventListenerを使ってイベントハンドラを追加する(一番オススメ)

です。

<input>が持つプロパティは山ほどありますから(alt, checked, list, max, min, name, readonly, size, src, type, value, width...などなど)、被らないようにするというのは意外と難しいです。
これはaddEventListenerをおすすめする理由の一つでもあります。


なぜ<input onclick="list()"> がinput要素 の list属性 を参照するのかというと、
HTMLに直接書いたonclickなどのイベントハンドラは、下のような環境で実行されることになっているためです。

javascript

1with(document){ 2 with(this.form){ // <form> 内の要素であれば 3 with(this){ // this とは onclick を記述した要素自身 4 /* 5 * この環境でコードが実行されます。 6 */ 7 } 8 } 9}

ですので、
<input onclick="value">と書いたら<input>のvalue属性が参照されますし、
<input onclick="submit">と書いたら<form>のsubmitメソッドが参照されますし、
<input onclick="write">と書いたらdocument.writeが参照されます。

参考:Qiita HTMLのイベント属性(onclickなど)のスコープについて
(参考ページではwith(document){}について触れられていませんが、上の例のようにdocumentのプロパティも確かに拾うので注意です。)

投稿2017/02/18 08:15

編集2017/02/20 09:51
kura

総合スコア368

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

Lhankor_Mhy

2017/02/18 08:20

げ、知らなかった。 てっきりグローバルスコープだと思ってました。 フォームだけスコープ変えるとか、ちょっとしたトラップですよねえ…… ありがとうございました。
maisumakun

2017/02/18 08:46

その場しのぎに「window.list()」で逃げることもできますけど、やはりイベントリスナー直書き自体、もはや「やめるべき書き方」かもしれませんね。
kura

2017/02/18 10:52

> maisumakunさん なるほど確かに「window.list()」という方法もありますね! addEventListenerがいいことには変わりないかもしれませんが、方法の一つとして覚えておきます。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.48%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問