How to use options object in Javascript's Function - javascript

I am trying this to get input as an argument with some objects,
function write(param) {
var str = param.str;
var elem = param.elem;
document.getElementById(elem).innerHTML= str;
}
and I'm passing this as an argument,
write({
elem:"op",
str:"Hello"
});
The thing I have to do is that I am having font tag with id 'op',
<font id="op"></font>
and when I run this I wont print Hello, as I have given Hello as an object parameter with op element for output.

I'm not sure where exactly your code has gone wrong. Here you can see that both the javascript and the html you produced should work together just fine.
function write(param) {
var str = param.str;
var elem = param.elem;
document.getElementById(elem).innerHTML = str;
}
write({
elem: 'op',
str: 'Hello'
})
<font id="op"></font>

As far as I'm seeing it, your code works as intended.
Answer for using an options object on a function:
In ES6 default parameters can prevent values to be undefined, however it does not actually compensate for the case that you're passing an object with missing parameters.
In this case I would suggest using Object.assign():
function write(options){
options = Object.assign({}, {
myDefaultParam: 'Hello',
elem: null,
str: ''
}, options);
if(options.elem) document.getElementById(options.elem).innerHTML = options.str;
}
What Object.assign() does is to merge a object of default options with the provided functions, allowing you to set default parameters that you can rely on. In this case write({}) would result in options being this object:
{
myDefaultParam: 'Hello',
elem: null,
str: ''
}
If this is overkill for you, I would suggest to simply check wether the keys are defined on your param object like this:
function write(param){
if(!param || !param.elem || !param.str) return false;
return document.getElementById(param.elem).innerHTML = param.str;
}

Related

Angular JS copy Object to another into a for loop

Trying to copy a part of a json object into another json object (thats a filter), into a for loop, under a conditional statement, it doesn't work.
This work but a plain to write an array:
$scope.candidats=[];
for (i=0;i<omegaCandidats.length;i++){
if (omegaCandidats[i].dateRdv==date){
$scope.candidats.push(
{
"id" :omegaCandidats[i].id,
"prenom" :omegaCandidats[i].prenom,
"nom" :omegaCandidats[i].nom,
"heure" :omegaCandidats[i].heure,
"dateRdv" :omegaCandidats[i].date
}
)
};
};
This doesn't work, and that's what i want to do. Its logical and should work:
$scope.candidats=[];
for (i=0;i<omegaCandidats.length;i++){
if (omegaCandidats[i].dateRdv==date){
$scope.candidats[i] = omegaCandidats[i];
};
};
This one work but only get one value of the for loop its useless:
$scope.candidats=[];
for (i=0;i<omegaCandidats.length;i++){
if (omegaCandidats[i].dateRdv==date){
$scope.candidats[0] = omegaCandidats[i];
};
};
what about using a filter:
$scope.candidats = omegaCandidats.filter(function(candidat){
return candidat.dateRdv == date;
});
You can use filter array method, try this:
$scope.candidats = omegaCandidats.filter(function(item) {
return item.dateRdv==date;
});
I think this should work :
$scope.candidats=[];
for (i=0;i<omegaCandidats.length;i++){
if (omegaCandidats[i].dateRdv==date){
//$scope.candidats.push(omegaCandidats[i]);
$scope.candidats.push(angular.copy(omegaCandidats[i]));
//copy will create a new reference for your object.
};
};
The code you had is not logical to me :
$scope.candidats=[];
for (i=0;i<omegaCandidats.length;i++){
if (omegaCandidats[i].dateRdv==date){
$scope.candidats[i] = omegaCandidats[i]; // This can't work because $scope.candidats[i] is not defined.
// You would also have an inconsistent array
};
};

Creating layered JSON object

I'm sure this is a simple question, but I can't find any information to help me, and I've been lost for a while. I'm trying to create a JSON object, and here is what I have so far:
var myJsonObject = new Object();
myJsonObject.context.applicationName = appName;
myJsonObject.context.ID = ID;
myJsonObject.context.domain = domain;
myJsonObject.context.production = "no";
myJsonObject.other.name = userName;
myJsonObject.other.date = userDate;
var myString = JSON.stringify(myJsonObject);
and here is what I want my JSON string to look like.
{
"context": {
"applicationName":"example",
"ID":"exampleID",
"domain":"someDomain",
"production","no"
},
"other": {
"name":"userName1",
"date":"userDate1"
}
}
However, I keep getting myJsonObject.context is undefined errors. I mean, I understand why it's happening, I never actually initialize it, but I don't know how to go about correcting this. Any help would be appreciated.
I'm guessing the myJsonObject.context has to be initialized as another object, and then I just add it to my original object as an array of objects....is this correct?
Yes, you need to first set it to an object, or you can just set them on the first line:
var myJsonObject = {context : {} , other: {} };
Also note that you can define your objects using a shorter syntax, like so:
var myJsonObject = {
context: {
applicationName: appName,
ID: ID,
domain: domain,
production: "no"
},
other: {
name: userName,
date: userDate
}
};
I'm guessing the myJsonObject.context has to be initialized as another object
Yes
and then I just add it to my original object
You'd generally do that at the same time
as an array of objects
No. You have nothing resembling an array there.
var myJsonObject = {};
myJsonObject.context = {};
myJsonObject.context.applicationName = appName;
Define myJsonObject.context = {}; property first.

object array not showing all variables

I have the code shown below.
My problem is: the part console.log(obj) is saying that Object {InternalNumber = 22 } and leaving out all the other variables.
I am expecting it to say:
Object { Id = someID, ParameterId="someParaId", InternalNumber = someNr, value="someValue"}
What might be wrong?
If you haven't noticed... I am saving the object to localStorage, and then retrieving it from there.
function getModel() {
var model = {
Id: '',
ParameterId: '',
InternalNumber: '',
Value: ''
}
return model;
}
function saveObjectToLocal() {
model = getModel();
model.Id = $(this).find(':input[name$=Id]').val();
model.ParameterId = $(this).attr('id');
model.InternalNumber = currentParcel.children('#viewModel_InternalNumber').val();
model.Value = $(this).find(':input[name$=Value]').val();
localStorage.setItem("model", JSON.stringify(model));
}
function getObjectFromLocalAndInsertInFields() {
obj = JSON.parse(localStorage.getItem("model"));
console.log(obj);
}
How are you calling saveObjectToLocal function. $(this) inside of that function is probably not matching anything because "this" is probably the global (window) object, and DOM elements aren't matched within the window object.
To see what I'm talking about. Run:
$(this);
$(this).find("input");
$(this).find("input").attr("id");
from your console. The first output will be length 1 of just window, the second would be an empty jQuery object, and the third would be undefined.
Calling .val() and .attr on an empty jQuery list would be undefined and therefore not serialized to JSON. InternalNumber is serialized because currentParcel.children is giving a match. You need to fix the $(this) selectors.
Json stringify function will exclude attributes with undefined value, so check first if the missing attributes have values

json nested lookup using string based key in javascript

With a javascript json object like this:
var data = {
blog : {
title: "my blog",
logo: "blah.jpg",
},
posts : [
{
title: "test post",
content: "<p>testing posts</p><br><p>some html</p>"
},
]
}
var lookup = "blog.title" //this gets generated from a template file
Now I know you can do something like, but these don't quite do what I need:
console.log(data['blog']); //works
console.log(data.blog.title); //works
console.log(data['blog']['title']); //works, but i dont know the depth of the lookup
But I need to be able to do something like the code below because I can't hardcode the structure, it gets generated and stored in lookup each time. Do I have to build this functionality using string cutting and recursion?? I really hope not
console.log(data['blog.title']); //does not work
console.log(data[lookup]); //does not work
EDIT....
Okay, possibly found a workaround. I don't know if this is safe or recommended practice, so comments on that would be great. Or alternative methods. So combining this with the code above.
var evaltest = "var asdf ="+JSON.stringify(data)+";\n"
evaltest += "asdf."+lookup
console.log(eval(evaltest)) //returns correctly "my blog" as expected
You could use dottie https://www.npmjs.org/package/dottie, which allows you to deep traverse an object using strings
var values = {
some: {
nested: {
key: 'foobar';
}
}
}
dottie.get(values, 'some.nested.key'); // returns 'foobar'
dottie.get(values, 'some.undefined.key'); // returns undefined
you could use:
data['blog']['title']
I've experimented with a couple ways of doing this including eval and using a dictionary lookup with switch(exp.length). This is the final version (comments stripped) I created:
var deepRead = function (data, expression) {
var exp = expression.split('.'), retVal;
do {
retVal = (retVal || data)[exp.shift()] || false;
} while (retVal !== false && exp.length);
return retVal || false;
};
//example usage
data = {
a1: { b1: "hello" },
a2: { b2: { c2: "world" } }
}
deepRead(data, "a1.b1") => "hello"
deepRead(data, "a2.b2.c2") => "world"
deepRead(data, "a1.b2") => false
deepRead(data, "a1.b2.c2.any.random.number.of.non-existant.properties") => false
Here's the Gist with full commenting: gist.github.com/jeff-mccoy/9700352. I use this to loop over several thousand items and have had no issues with deep-nested data. Also, I'm not wrapping in try/catch anymore due to the (small) performance hit: jsPerf.

How can I conditionally modify the contents of a global object?

I have a global var named inputType which is a lengthy object:
inputType = {
part1: 'string',
part2: 'string2',
...
part100:'last string'
}
In a separate piece of code, I have some input fields that receive numeric values. I would like to alter certain parts of the var object string as such:
<input id='input1'>First input
code:
$(document).ready(function(){
$('#input1').blur(function (){
var inp = parseInt($('#input1').val(), 10);
if (inp <10) {
inputType.part2.replace(/string2/,'some other string');
}
});
});
// Then I call this modified inputType.part2 object in another function
// I can't seem to effect the string change when the condition is met? When I try to call this particular object property in another script, the string change is not performed. I also can't see this change on the DOM inspector when I try this out. But this syntax will perform the replace function when I try it on the console.
How can I replace or modify inputType.part2 when the condition is met, and then use the modified object in another piece of code?
Objects are tough!
Thanks.
Name your object first. Then try to access it with that name.
var xObj = {
part1: 'string',
part2: 'string2',
...
part100:'last string'
}
.....
if (inp <10) {
xObj.part2.replace(/string2/,'some other string');
}
Edit:
.replace() will not modify the source string. we have to assign the result of .replace() back to the source to accomplish the modification.
Conceptual DEMO
Your code should be like this,
if (inp <10) {
xObj.part2 = xObj.part2.replace(/string2/,'some other string');
}
Please read here to know more about .replace()
Try this:
window.InputVal = {
part1: 'string',
part2: 'string2',
...
part100:'last string'
}
.....
if (inp <10) {
window.InputVal.part2 = window.InputVal.part2.replace(/string2/,'some other string');
}
just 'update' the window.InputVal.part2 with the new value. Put only the .replace will not override the old value.
For example:
// define "x"
window.InputVal.x = 1;
// replace value
window.InputVal.x.toString().replace(/1/,'2');
// show
console.log(window.InputVal.x)
// will print 1
// but..if you do:
window.InputVal.x = window.InputVal.x.toString().replace(/1/,'2');
// will print '2'

Categories