jsFiddleでAngularJSを使おうと思って以下のような簡単なコードを実行してみるとUncaught objectというエラーがでてくる。
<div ng-app="myApp">
<div ng-controller="testCtrl">
{{hoge}}
</div>
</div>
var app = angular.module('myApp', []);
app.controller('testCtrl', function ($scope){
$scope.hoge = 'hello';
});
この問題の解決方法はAngularJS jsFiddleとかでぐぐればすぐに出てくる。
Using jsFiddle with AngularJS
解決法
左のFrameworks & ExtensionsのonLoad
となっているセレクトボックスをNo wrap -in<body>
に変更してやればよい。
jsFiddleでの修正例
なぜ起こるのか
左のセレクトボックスをonLoad
の状態で実行するとjsFiddleは以下の用なソースを出力する。(関係のない部分は省略, 見やすいようにインデントなどを変更)
<html>
<head>
<meta http-equiv="content-type" content="text/html; charset=UTF-8">
<title> - jsFiddle demo</title>
<script type="text/javascript" src="//cdnjs.cloudflare.com/ajax/libs/angular.js/1.2.1/angular.js"></script>
<script type="text/javascript">//<![CDATA[
window.onload=function(){
var app = angular.module('myApp', []);
app.controller('testCtrl', function ($scope){
$scope.hoge = 'hello';
});
}//]]>
</script>
</head>
<body>
<div ng-app="myApp">
<div ng-controller="testCtrl">
{{hoge}}
</div>
</div>
</body>
</html>
このソースを見るとjsがwindow.onload
のタイミングで実行されるように設定されている。
AngularJSはng-app
を見つけるとDOMContentLoaded
のタイミングで初期化を行う。
その時にはまだmyapp
モジュールが定義されていないのでモジュールが見つからないというエラーを出す。
参考:AngularJSの起動 | AngularJS 1.2 日本語リファレンス | js STUDIO
なぜNo wrap -in<body>にすると解決できるのか
jsFiddleの左のセレクトボックスをNo wrap -in<body>
に設定するとbody
タグの最後に、No wrap -in<head>
に設定するとhead
タグの最後に直接jsが埋め込まれる。
この時のjsはwindow.onload
などでラップされないためDOMContentLoaded
のタイミングで既にモジュールが定義されている。
よってこの修正を行うとAngularJSがエラーを出さないようになる。
他の解決法
ng-app
があることによってAngularJSが自動起動しようとする。
この自動起動によって問題が起こるため、ng-app
を取り除き、AngularJS手動起動することでもこの問題を回避することができる。
<div>
<div ng-controller="testCtrl">
{{hoge}}
</div>
</div>
var app = angular.module('myApp', []);
app.controller('testCtrl', function ($scope){
$scope.hoge = 'hello';
});
angular.bootstrap(document, ['myApp']);