I'm getting an Object doesn't support property or method error when I try to call a function in a dojo module. I have a main page and two modules. I call the first module from the main page and it works, I call the second module from the first and it works, but I get the error when I try to call the first module from the second. Here is my code:
main page:
<!DOCTYPE html>
<html >
<head>
<meta name="viewport" content="initial-scale=1, maximum-scale=1,user-scalable=no"/>
<link rel="stylesheet" href="http://js.arcgis.com/3.10/js/dojo/dijit/themes/claro/claro.css">
<link rel="stylesheet" href="http://js.arcgis.com/3.10/js/esri/css/esri.css">
<script>
var dojoConfig = {
parseOnLoad:true,
async: true,
isDebug:true,
packages: [
{name: "Scripts", location: location.pathname.replace(/\/[^/]+$/, "") + "/Scripts"},
]
};
</script>
<script> src="http://js.arcgis.com/3.10/"></script>
<script>
require(["Scripts/Mod1", "Scripts/Mod2"],
function (Mod1, Mod2) {
Mod1.M1Method("call from main page");//works great
});
</script>
</head>
<body class="claro">
<div>look here you</div>
</body>
</html>
Module 1:
define(["Scripts/Mod2"],
function (Mod2) {
return {
M1Method: function (msg) {
alert(msg);
Mod2.M2Method("call from Mod1");//works great
},
M1Method2: function (msg) {
alert(msg);
}
}
});
Module 2:
define(["Scripts/Mod1"],
function (Mod1) {
return {
M2Method: function (msg) {
alert(msg);
Mod1.M1Method2("call from Mod2"); //JavaScript runtime error: Object doesn't support property or method 'M1Method2'
}
}
});
How can I make that call from Mod 2 to Mod1?
Thanks
You are trying to do a cyclic dependency. In module 2, use a require statement. Try something like this:
define(["require"],
function (require) {
return {
M2Method: function (msg) {
alert(msg);
try {
require(["Scripts/Mod1"], function(Mod1) {
Mod1.M1Method2("call from Mod2");
});
} catch (dohObj) {
alert('Doh!, this failed. Stupid answer: ' + dohObj.message);
}
}
}
}
);
Your html code has a typo in that you enclosed the 'script' tag too soon when including dojo.js. Should be something like
<script type="text/javascript" src="http://js.arcgis.com/3.10/"></script>
You need to fix that file first to properly include dojo and 'require()'.
Related
I am trying to implement the following JSON file in my HTML page.
<html>
<head>
<title> test get</title>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.12.4/jquery.min.js">
<script>
$(function() {
$.getJSON('json.json',function(data) {
$.each(data.quotes,function(key,value) {
alert( key+ "said by "+value);
});
});
});
</script>
</head>
<body>
</body>
</html>
Here is the JSON that i am working on.
{
"quotes": {
"hey there":"randomguy1",
"wassup":"randomguy2",
"coool":"randomguy3"
}
}
I have checked different tutorials and similar questions at stackoverflow still couldn't figure out the mistake.
Just fix your script code,
You MUST close the <script ...jquery> tag.
<html>
<head>
<title>test get</title>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.12.4/jquery.min.js"></script>
<script>
$(function () {
$.getJSON('json.json', function (data)
{
$.each(data.quotes, function (key, value) {
alert(key + "said by " + value);
});
});
});
</script>
</head>
<body> </body>
</html>
You can achieve it in a different manner. Use ajax to load a file content and parse it as a json.
$.ajax({
url : "helloworld.json",
success : function (data) {
//TODO parse string to json
}
});
I am trying to call this Javascript function. When I hit my button, there is nothing loading. I set an id for my button. With the onclick I load the function onLinkedInLoad. But is it not that function I should call to activate the script? Can anybody see what I am doing wrong here?
<!DOCTYPE html>
<html>
<head>
<title></title>
<meta charset="utf-8" />
</head>
<body>
<button id="btn">Try Me</button>
<script type="text/javascript">
document.getElementById("btn").onclick = onLinkedInLoad;
</script>
<script type="text/javascript" src="//platform.linkedin.com/in.js">
api_key: myKey
authorize: true
onLoad: onLinkedInLoad
</script>
<script type="text/javascript">
// Setup an event listener to make an API call once auth is complete
function onLinkedInLoad() {
IN.Event.on(IN, "auth", shareContent);
}
// Handle the successful return from the API call
function onSuccess(data) {
console.log(data);
}
// Handle an error response from the API call
function onError(error) {
console.log(error);
}
// Use the API call wrapper to share content on LinkedIn
function shareContent() {
// Build the JSON payload containing the content to be shared
var payload = {
"comment": "Check out developer.linkedin.com! http://linkd.in/1FC2PyG",
"visibility": {
"code": "anyone"
}
};
IN.API.Raw("/people/~/shares?format=json")
.method("POST")
.body(JSON.stringify(payload))
.result(onSuccess)
.error(onError);
}
</script>
</body>
</html>
Update:
I get this in my console:
18 Uncaught ReferenceError: onLinkedInLoad is not defined
www.linkedin.com/uas/js/userspace?v=0.0.1191-RC8.56309-1429&apiKey=myKey&authorize=true&onLoad=onLinkedInLoad&secure=1&:
22 Uncaught Error: You must specify a valid JavaScript API Domain as part of this key's configuration.
I putted my APIkey in also. I just replaced in the code here with "myKey". I also tried with .addEventListener('click', onLinkedInLoad), but still nothing happens
Try to load the function definition script before the call script. Or better, take all the scripts in another file and just load that on your HTML.
I've tried your code on js fiddle and it works by doing that.
Im trying to call a function from another js file that is located in the same application directory as my main js script and html file. I receive an error claiming that the referenced function does not exist. I have referenced both of the scripts in the main html file in the proper order but cant for the life of me figure out why it cannot detect the function. I can only assume it has something to do with how dojo parses through the files and have experimented with both its dojo/domReady! and dojo/ready modules in hopes to force scripts to load. I feel like this should be much simpler than Im making it out to be. Any help would be greatly appreciated.
html
<!DOCTYPE html>
<html>
<head>
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<title>Asset View</title>
<meta charset="utf-8">
<link rel="stylesheet" href="http://js.arcgis.com/3.14/dijit/themes/claro/claro.css">
<link rel="stylesheet" href="http://js.arcgis.com/3.14/esri/css/esri.css">
<link rel="stylesheet" href= "styles/styles.css">
<script src="http://js.arcgis.com/3.14/"></script>
<script src="scripts/requests-js.js"></script>
<script src="scripts/layout-js.js"></script>
<script src="scripts/xmain-js.js"></script>
</head>
<body class = "claro">
</body>
</html>
requests-js.js
require(["dojo/dom","dojo/on","dojo/request","dojo/json","dojo/parser","dojo/ready"
], function(dom,on,request,JSON,parser,ready) {
ready(function() {
console.log("request start");
function sendRequest (url,assetCode,fromDate,toDate) {
console.log("Request innit");
request(url,{
method: "POST",
handleAs: "json",
headers: {"Content-Type": "application/json"},
data: JSON.stringify(
[
{
"AssetCodes": assetCode,
"FromGasDay": fromDate,
"ToGasDate": toDate
}
]
)
}).then(function(resp){
console.log(JSON.stringify(resp));
var naStorageJSON = resp;
});
}
console.log("request end");
});
});
main-js.js
require([
"dojo/dom","dojo/on","dojo/parser","dojo/json","dojo/request","dojo/ready"
], function(dom,on,parser,JSON,request,ready) {
ready(function() {
console.log("Main Start");
var url = "http://*********";
var assetCode = ["**"];
var toDate = "****";
var fromDate ="*****";
on(dom.byId("senecaLakeBtn"),"click", sendRequest(url,assetCode,toDate,fromDate));
console.log("Main End");
});
});
The issue is scope here. By declaring an empty array at the top of the js script (outside of its successive functions) the function can be accessible to other scripts in the application.
var app = [];
require(["dojo/dom","dojo/on","dojo/request","dojo/json","dojo/parser","dojo/ready"
], function(dom,on,request,JSON,parser,ready) {
ready(function(){
app.sendRequest = function sendRequest (url,assetCode,fromDate,toDate) {
...
...
}
}
it can them be called upon from other scripts by referencing
app.sendRequest(arg1,arg2,arg3);
I am learning dojo
i have created a dojo class using declare as below
require(
["dojo/_base/declare"],function(declare){
return declare(null,{
constructor : function(){
alert("done");
}
});
});
and this is save in /learnDojo/root/test.js
and the index.html as below
<!DOCTYPE html>
<html>
<head>
<title></title>
</head>
<script type="text/javascript">
var dojoConfig = {
async: false,
parseOnLoad: false,
isDebug : true,
packages:[
{ name:"base",
location:"/learnDojo/root"
}]
};
</script>
<script src="//localhost:8080/dojo1.9.0/dojo/dojo.js" type="text/javascript"></script>
<script type="application/javascript">
require(["base/test","dojo/_base/declare","dojo/domReady!"],function(test,declare){
var test = new test();
});
</script>
<body>
</body>
</html>
i have the index.html in the /learnDojo which is in webapps folder of the tomcat
When i load this from browser i am getting the error "Uncaught TypeError: number is not a function"
Why? any issue with code or dojo syntax for creating the class
When defining Dojo modules you should be using define(), not require(). So your /learnDojo/root/test.js file would look like this:
define(
["dojo/_base/declare"],function(declare){
return declare(null,{
constructor : function(){
alert("done");
}
});
});
The reason for this is that define() will actually return the object/value you returned in your callback (in this case the return declare(...) statement. A require() however will not return that value, causing strange errors.
For jQuery template:
http://api.jquery.com/category/plugins/templates/
I want to be able to dynamically load the templates from a server, rather than predefining it on the page.
The demos I saw on the projects are using predefined templates. After some research I found out that it is possible.
I try doing this and it doesn't work:
<script src="child.html" type="text/x-jquery-tmpl"></script>
I tried doing this and it doesn't work:
$(function () {
$.get("child.html", function (data) {
//Add template
$.template("tmplChild", data);
});
//template binds before async call is done
$.tmpl("tmplChild").appendTo("body");
});
And finally, I have get it down to the following hack:
so.html (This is the main page):
<html>
<head>
<title></title>
</head>
<body>
<script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jquery/1.4.3/jquery.min.js"></script>
<script type="text/javascript" src="http://ajax.microsoft.com/ajax/jquery.templates/beta1/jquery.tmpl.js"></script>
<script type="text/javascript" src="so.js"></script>
<script type="text/javascript">
$(function () {
initTemplates(templateReady);
});
function templateReady() {
$.tmpl("tmplChild").appendTo("body");
}
</script>
</body>
</html>
child.html (This is the child template)
<h1>Child Loaded</h1>
so.js (This is my hack for ajaxly loading the js templates)
function initTemplates(callback) {
var templateUrl = "child.html";
var templateName = "tmplChild";
initTemplate(templateUrl, templateName, callback);
}
function initTemplate(url, name, callback) {
var opts =
{
type: "GET",
url: url,
dataType: ($.browser.msie) ? "text" : "xml",
success: function (data) {
xmlCallback(data, name, callback);
},
error: function (x) {
xmlCallback(x.responseText, name, callback);
}
}
$.ajax(opts);
}
function xmlCallback(data, name, callback) {
if (typeof data != "string") {
if (window.ActiveXObject) {
var str = data.xml;
data = str;
}
// code for Mozilla, Firefox, Opera, etc.
else {
var str = (new XMLSerializer()).serializeToString(data);
data = str;
}
}
//only takes strings!
$.template(name, data);
callback();
}
And here's what I don't like about it.
This doesn't work on Chrome
It seems like a lot of code just to load some template
I lost the ability to use $(document).ready(). I must now put all my code in this templateReady() method to be "template safe".
Is there a way around this?
Thanks,
Chi
Just load the template body as simple text and forget about putting it in a dummy <script> block. You can use $.tmpl(body, params) to populate the template and turn it into a string for appending to the DOM.
The whole thing with "not really script" <script> blocks is just a convenience useful in some situations.
edit — example:
$.get("/some/url/for/a/template", function(templateBody) {
var expandedTemplate = $.tmpl(templateBody, { param1: 0, param2: "Hello World" });
});
If the goal is to fetch a unique template each time you get data via ajax, then you might try fetching the template at the same time and include it in your data, that is if you have the luxury of modifying the returned object (anonymous object in .Net). Then you can store the template anywhere you want and you only need 1 ajax call for both the data and the template.
Refer here:
https://www.npmjs.com/package/jlate
use CDN:
<script src="https://cdn.jsdelivr.net/combine/npm/lodash,npm/jlate#0.0.2/jlate/JLate.min.js"></script>
HTML Code:
<body>
<div>
<jlate id="my_temp" src="template/jlate_title.html" type="template">
Loading...
</jlate>
</div>
</body>
Javascript:
$$("#my_temp").jlate({ title: "sample title"});