Concatenate for...in into single string - javascript

I have an object of URL parameters that I had originally appended to a form using this method, but I am attempting to adjust that to also create a single string concatenated from each of the values of the inputs to then.
I have this code here, which creates the inputs and prepends them to the top of the form:
for (property in parameters) {
$('<input>', {
type: 'hidden',
id: `${property}`,
class: 'urlparameter',
name: `${property}`,
value: `${property}: ${parameters[property]}`
}).prependTo('form');
}
That code creates this inputs, from the testing URL I am currently using:
<input type="hidden" id="utm_content" class="urlparameter" name="utm_content" value="utm_content: comm">
<input type="hidden" id="utm_medium" class="urlparameter" name="utm_medium" value="utm_medium: email">
<input type="hidden" id="utm_source" class="urlparameter" name="utm_source" value="utm_source: sig">
From there, I am trying to loop through all the inputs with the class urlparameter and grab the value and append it to the previous input value for a single string. Right now I am just trying to console.log them just for testing sake. No matter what I do, it keeps listing them all individually, or I break the syntax and can't figure out how to fix it.
The only way that comes close is this:
var inputs = $(".urlparameter");
for(var i = 0; i < inputs.length; i++){
let inputvalue = $(inputs[i]).val();
console.log(inputvalue + ",");
}
This creates the following:
utm_content: comm,
utm_medium: email,
utm_source: sig,
What I am trying to get is:
utm_content: comm, utm_medium: email, utm_source: sig,
How do I get them all to iterate and add to a single string on one line?

Use .map() and .join().
console.log(inputs.map((i, el) => el.value).get().join(','));

You can use .map to get all the values, convert to an array, then call Array#join.
let res = $(".urlparameter").map((i, el) => $(el).val()).toArray().join(', ');
console.log(res);
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<input type="hidden" id="utm_content" class="urlparameter" name="utm_content" value="utm_content: comm">
<input type="hidden" id="utm_medium" class="urlparameter" name="utm_medium" value="utm_medium: email">
<input type="hidden" id="utm_source" class="urlparameter" name="utm_source" value="utm_source: sig">

I would suggest using reduce, which is JavaScript's version of an accumulator.
console.log(
Array.prototype.reduce.call($('input.urlparameter'),(p,v) => p + v.value + ', ',"")
);
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<input type="hidden" id="utm_content" class="urlparameter" name="utm_content" value="utm_content: comm">
<input type="hidden" id="utm_medium" class="urlparameter" name="utm_medium" value="utm_medium: email">
<input type="hidden" id="utm_source" class="urlparameter" name="utm_source" value="utm_source: sig">

Related

target multiple empty input fields with same id containing brackets

I have a couple of input fields with the following ID:
<input type="text" name="numberC[]" id="numberC[]">
<input type="text" name="numberC[]" id="numberC[]">
<input type="text" name="numberC[]" id="numberC[]">
I fetch data in JSON format via my ajax call and push() certain values in my array.
How could I create a loop that will loop through the array and then inserts each value in one of the above input fields?
so let's say I have the following array:
var testArray = ['hi', 'bye', 'stackoverflow'];
and I have the following 3 input fields:
<input type="text" name="numberC[]" id="numberC[]">
<input type="text" name="numberC[]" id="numberC[]">
<input type="text" name="numberC[]" id="numberC[]">
Whenever I loop through it I unfortunately get the highest value in all of my input fields.
I try to loop through my array in JavaScript and insert each value in each input field. so testArray[0] should go in the first input field, testArray[1] in the second input field and testArray[2] in the third.
Sources I used: Find DOM element by ID when ID contains square brackets?
The id in dom is always unique.Instead use document.querySelectorAll to get all the element with same name then loop through them and use the index to check if an element exist in the index of testArray. If so then set the value of the input
var testArray = ['hi', 'bye', 'stackoverflow'];
document.querySelectorAll('[name="numberC[]"]').forEach(function(item, index) {
if (testArray[index]) {
item.value = testArray[index]
}
})
<input type="text" name="numberC[]" id="numberC[1]">
<input type="text" name="numberC[]" id="numberC[2]">
<input type="text" name="numberC[]" id="numberC[3]">
If you change your HTML to have different ids
<input type="text" id="numberC[1]"/>
<input type="text" id="numberC[2]"/>
<input type="text" id="numberC[3]"/>
you can easily set the values like this:
var testArray = ['hi', 'bye', 'stackoverflow'];
for(let i in testArray) {
document.querySelector('#numberC\\[' + (+i+1) + '\\]').value = testArray[i];
}

What is the best way of getting the values that will be typed at dynamically generated inputs

I've got a form that creates inputs dynamically.
An example of it would be something like this:
<form>
<input name="item[0][name]">
<input name="item[1][name]">
</form>
The 0 and 1 being the id of the item.
Note that the 0 and 1 could be 15 and 49, or even 520, 854 and 2.
There's no order neither ordination and, there is also no limit for being only two items.
The question is:
"What is the best way of getting the values that will be typed at those inputs, before sending them to the backend?"
The only way I can think of is adding ids when generating the form, but that doesn't seem elegant at all.
If you cant figure a better way, that would be lovely =)
You can use document.querySelectorAll() and Attribute Selector
function submit() {
let inputs = document.querySelectorAll('input[name*=item]');
let values = Array.from(inputs).map(({value})=>value);
console.log(values);
}
<form>
<input name="item[0][name]">
<input name="item[1][name]">
</form>
<button onclick="submit()">Sumbit</button>
Try
function submit() {
let inputs = document.querySelectorAll('input');
let values = [...inputs].map(x=>x.value);
console.log(values);
}
<form>
<input name="item[0][name]">
<input name="item[1][name]">
</form>
<button onclick="submit()">Send</button>
You could use the HTMLFormElement.elements property.
const formInputs = document.getElementById('a-form').elements
const dataObject = {}
for (let i = 0; i < formInputs.length; i++) {
dataObject[formInputs[i].name] = formInputs[i].value
}
console.log(dataObject)
<form id="a-form">
<input type="text" name="item[0][name]" />
<input type="text" name="item[1][name]" />
<input type="text" name="item[2][name]" />
</form>
Set a specific data attribute (for instance data-my-input) on them, then use querySelectorAll(‘input[data-my-input]’) to get them all and send them to your backend.

how to push object ino an array when user inputs value in angularJs

I have multiple input fields under different headings:-
<label>User</label>
<input type="text" ng-model="a.arr.username" name="arr[0]"/>
<input type="text" ng-model="a.arr.userdob" name="arr[0]"/>
<input type="text" ng-model="a.arr.userpanNo" name="arr[0]"/>
<label>Employee</label>
<input type="text" ng-model="a.arr.empname" name="arr[1]"/>
<input type="text" ng-model="a.arr.empdob" name="arr[1]"/>
<input type="text" ng-model="a.arr.emppanNo" name="arr[1]"/>
<label>Daily Workers</label>
<input type="text" ng-model="a.arr.dwname" name="arr[2]"/>
<input type="text" ng-model="a.arr.dwdob" name="arr[2]"/>
<input type="text" ng-model="a.arr.dwpanNo" name="arr[2]"/>
I want to save above data in the format:- [{a.arr.username:any value},{a.arr.empname:any value},{a.arr.dwname:any value}]. But the structure I am getting is:- {a.arr.username:any value,a.arr.empname:any value,a.arr.dwname:any value}.
Is there any way to do this?
Where you are storing data you will have to store it like :
a.arr=[];
//here you have to define object for each index before making keys of it.
a.arr[i]={};
Try this
var arr=[]; arr.push({'a.arr.username':$scope.a.arr.username,{'a.arr.empname':$scope.a.arr.empname}})
Basically, you want to make your object as an array of it's properties. I suggest you to leave the code as it is and just add a code to make another controller property which will hold the array of those properties.
To get the array of properties, below code will help you:
var x = {username: "any value", empname: "any value", dwname: "any value"};
var newArr = [];
var properties = Object.keys(x);
for(var i=0;i<properties.length;i++){
newArr.push({});
newArr[newArr.length - 1][properties[i]] = x[properties[i]];
};
Let me know if you need to understand anything else regarding this.
Best Regards

How to parse two-dimensional checkbox name into JSON with matching indices?

One of our clients' sites has a form that we hijack and submit via AJAX. Recently we got a request to have it support a fluid list of checkboxes with predefined indices in the name - and I'm a little stumped as to how to properly parse this into an array.
Here's an example:
<li><input type="checkbox" name="group[69][4096]" /> Thin</li>
<li><input type="checkbox" name="group[69][8192]" /> Oily</li>
<li><input type="checkbox" name="group[69][16384]" /> Dry</li>
The first- and second-level indices are going to change on a regular basis, so they can't be hard-coded. How can I create a two-dimensional javascript array and place these values under the same keys?
For obvious reasons I don't want to use eval(), and I tried my hand at regex but I'm afraid it isn't my strong suit. I got close - .+\[([0-9]+)\]\[([0-9]+)\] will match the string on http://regexr.com/ - but it doesn't seem to work in js for some reason. At least, I can't get it to return the captured groups.
You could reduce the inputs into a 2d array by parsing each input's name with this regexp /group\[(\d*?)\]\[(\d*?)\]/:
const inputs = Array.from(document.querySelectorAll('[name^="group"]'));
const grid = inputs.reduce((grid, input) => {
const [, y, x] = input.name.match(/group\[(\d*?)\]\[(\d*?)\]/);
grid[y] = grid[y] || [];
grid[y][x] = input.value;
return grid;
}, []);
console.log(grid);
<input name="group[0][0]" value="0,0"/>
<input name="group[0][1]" value="0,1"/>
<input name="group[0][2]" value="0,2"/>
<input name="group[0][3]" value="0,3"/>
<input name="group[0][4]" value="0,4"/>
<input name="group[1][0]" value="1,0"/>
<input name="group[1][1]" value="1,1"/>
<input name="group[1][2]" value="1,2"/>
<input name="group[1][3]" value="1,3"/>
<input name="group[1][4]" value="1,4"/>
<input name="group[2][0]" value="2,0"/>
<input name="group[2][1]" value="2,1"/>
<input name="group[2][2]" value="2,2"/>
<input name="group[2][3]" value="2,3"/>
<input name="group[2][4]" value="2,4"/>

Why 1. returns an empty string when I try to get value of an input type number using javascript and html5?

I have a normal input as follows:
<input type="number" name="quantity" id="myInput">
If I type "1." (without the quotes of course) when I try to get the value of the input with
document.getElementById("myInput").value
Only an empty string is obtained.
Is there any other way to get the "1." input with javascript?
Edit
I am working using Polymer 1.0 and databinding, so in my example I showed using normal JavaScript syntax with the intention of finding a solution to my problem using only javascript.
I just want to know how to access a property that returns the value of the input, and which I believe should be stored in some property of the object.
If you use <input type="number"> the element is enriched with an extra attribute, valueAsNumber. So instead of
document.getElementById("myInput").value
use
document.getElementById("myInput").valueAsNumber
valueAsNumber will return NaN instead of blank if the value entered in the input not is convertable to a number. There is also a validity attribute holding information of the status of the current value, both according to the value as supposed number but also according to the number input's settings, i.e "why is the number invalid".
Fun with number inputs, try this out in various browsers :
<input type="number" name="quantity" id="myInput" ><br>
<input type="text" id="value" ><br>
<input type="text" id="valueAsNumber" ><br>
<input type="text" id="validity" ><br>
document.getElementById("myInput").onkeyup = function() {
document.getElementById("value").value = this.value;
document.getElementById("valueAsNumber").value = this.valueAsNumber;
document.getElementById("validity").value = '';
for (validity in this.validity) {
if (this.validity[validity]) {
document.getElementById("validity").value+=validity+' ';
}
}
}
actually quite informative, if you want to investigate exactly why you get an empty value back from the input -> http://jsfiddle.net/oaewv2Lr/ Have tried with Chrome, Opera and FF - Chrome seems to be the most "forgiving" browser of those three.
I found a way to get invalid values:
Focus the input.
Select its contents using execCommand().
Grab the selection using window.getSelection().
Example:
document.querySelector('input[type="submit"]').addEventListener('click', function() {
var inp= document.getElementById('myInput');
inp.focus();
document.execCommand('SelectAll');
var value = window.getSelection().toString();
document.getElementById('output').textContent = value;
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<input type="number" name="quantity" id="myInput">
<input type="submit">
<div id="output"></div>
It won't work if you will enter 1., as 1. is not a valid number.
Update: It seems that your use of type="number" means that certain values won't come back. You can switch it to a type="text" and do the checking yourself:
document.getElementById('mySubmit').addEventListener('click', function() {
var value = document.getElementById('myInput').value;
if ( value != parseFloat(value) )
alert('Invalid Number');
document.getElementById('myOutput').innerHTML = value;
});
<input type="text" name="quantity" id="myInput">
<input type="submit" id="mySubmit">
<div id="myOutput"></div>

Categories

Resources