Parsing text area line that comma separated using Jquery or Js - javascript

I have a textarea with data like this (UserId,Name,Gender), and I want to parsing that data
<textarea class="form-control" id="data" rows="5" cols="10" placeholder="ID's Phones Number:" name="msg">097544,markd amm,male
731490,Hossam Hassan,male
130578,Kamal Eldin,male
87078148,Muhammad Ahmad Atia,male
932484,Alia AlHorria,female
093779,Yaser Hadidi,male
39393,Soka Dą,female
</textarea>
i want all IDs only , Names only And i want to get Names&Gender from text area above ,
i tried to separated this data but if failed .
This my JS code :
var data = $('#data').val();
console.log(fbdata[0]);

Split your trimmed string by newlines to create an array of strings.
Then, depending on the desired output use Array.prototype.map() or Array.prototype.reduce()
const elData = document.querySelector("#data");
const str = elData.value.trim();
const lines = str.split(/\n/);
// Example 1: create array or data objects
const list = lines.map(str => {
const [id, name, gender] = str.split(",");
return {id, name, gender};
});
// console.log(list); // get 'em all
console.log(list[1]); // get by index
// Log only names
list.forEach((user) => {
console.log(user.name);
});
// example 2: create Object of items - by ID
const listById = lines.reduce((acc, str) => {
const [id, name, gender] = str.split(",");
acc[id]= {id, name, gender};
return acc;
}, {});
// console.log(listById); // get 'em all
console.log(listById[731490]) // Get specific by ID
<textarea class="form-control" id="data" name="msg">097544,markd amm,male
731490,Hossam Hassan,male
130578,Kamal Eldin,male
87078148,Muhammad Ahmad Atia,male
932484,Alia AlHorria,female
093779,Yaser Hadidi,male
39393,Soka Dą,female
</textarea>

You could also do it like this.
var results = [];
var data = $('#data').val().trim();
if(data) {
// Create an array by splitting the textarea.value by newline
data = data.split(/\r?\n/);
// Loop through indivdual rows, and split by comma / ,
for(var i = 0; i < data.length; i++) {
var temp = data[i].trim();
if(temp) {
// Create an array from the values in the current line
temp = temp.split(",");
// Separate the first and last names
var pairs = temp[1].split(/ (.*)/s);
// if there's no last name, pairs[1]
// will be undefined, so we set it to
// and empty string, to avid errors
if(typeof pairs[1] === 'undefined') {
pairs[1] = '';
}
var personsObj = {};
personsObj.id = temp[0];
personsObj.firstName = pairs[0].trim();
personsObj.lastName = pairs[1].trim();
personsObj.gender = temp[2].trim();
results.push(personsObj);
}
}
}
console.log(results);
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<textarea class="form-control" id="data" rows="5" cols="10" placeholder="ID's Phones Number:" name="msg">097544,markd amm,male
731490,Hossam Hassan,male
130578,Kamal Eldin,male
87078148,Muhammad Ahmad Atia,male
932484,Alia AlHorria,female
093779,Yaser Hadidi,male
39393,Soka Dą,female
</textarea>
EDIT
If you want to replace the contents of the textarea with specific values from the processed array of objects (results, in my example), you could do that like this.
Please note that you do not need extra textareas, like in the following example. I am using them to show you what you would get for different combinations. In reality, you would replace the contents of the #data element with the new content.
var results = [];
var data = $('#data').val().trim();
if(data) {
// Create an array by splitting the textarea.value by newline
data = data.split(/\r?\n/);
// Loop through indivdual rows, and split by comma / ,
for(var i = 0; i < data.length; i++) {
var temp = data[i].trim();
if(temp) {
// Create an array from the values in the current line
temp = temp.split(",");
// Separate the first and last names
var pairs = temp[1].split(/ (.*)/s);
// if there's no last name, pairs[1]
// will be undefined, so we set it to
// and empty string, to avid errors
if(typeof pairs[1] === 'undefined') {
pairs[1] = '';
}
var personsObj = {};
personsObj.id = temp[0];
personsObj.firstName = pairs[0].trim();
personsObj.lastName = pairs[1].trim();
personsObj.gender = temp[2].trim();
results.push(personsObj);
}
}
}
// This doesn't have to be here, you can use the logic in the loop above
// which would a better, more efficient way of doing it
// I'm doing this separately, so you can better understand how it works
// That's why there are 6 additional textareas - in reality, you would
// change the contents of your original textarea
var tmpNames = "", tmpIdsNames = "",
tmpGenders = "", tmpIdsGenders = "",
tmpNamesGenders = "", tmpIdsNamesGenders = "";
for(var i = 0; i < results.length; i++) {
tmpNames += results[i].firstName+ "\r\n";
tmpIdsNames += results[i].id + "," + results[i].firstName + "\r\n";
tmpGenders += results[i].gender + "\r\n";
tmpIdsGenders += results[i].id + "," + results[i].gender + "\r\n";
tmpNamesGenders += results[i].firstName + "," + results[i].gender + "\r\n";
tmpIdsNamesGenders += results[i].id + "," + results[i].firstName + "," + results[i].gender + "\r\n";
}
$("#justNames").val(tmpNames);
$("#idsNames").val(tmpIdsNames);
$("#justGenders").val(tmpGenders);
$("#idsGenders").val(tmpIdsGenders);
$("#namesGenders").val(tmpNamesGenders);
$("#idsNamesGenders").val(tmpIdsNamesGenders);
textarea {
width: 100%;
}
.results {
display: inline-block;
width: 30%;
margin-right: 15px;
}
.results textarea {
min-height: 75px;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<label style="display:block; width:100%">Original data
<textarea class="form-control" id="data" rows="5" cols="10" placeholder="ID's Phones Number:" name="msg">097544,markd amm,male
731490,Hossam Hassan,male
130578,Kamal Eldin,male
87078148,Muhammad Ahmad Atia,male
932484,Alia AlHorria,female
093779,Yaser Hadidi,male
39393,Soka Dą,female
</textarea>
</label>
<label class="results">Just names
<textarea style="display:block" id="justNames" name="justNames"></textarea>
</label>
<label class="results">IDs and names
<textarea style="display:block" id="idsNames" name="idsNames"></textarea>
</label>
<label class="results">Just genders
<textarea style="display:block" id="justGenders" name="justGenders"></textarea>
</label>
<label class="results">IDs and genders
<textarea style="display:block" id="idsGenders" name="idsGenders"></textarea>
</label>
<label class="results">Names and genders
<textarea style="display:block" id="namesGenders" name="namesGenders"></textarea>
</label>
<label class="results">IDs, names and genders
<textarea style="display:block" id="idsNamesGenders" name="idsNamesGenders"></textarea>
</label>
You can also experiment with this fiddle.

See String.prototype.split() and Array.prototype.map().
var data = $('#data').val().split("\n").map(line => line.split(",")[0]);
// ['097544', '731490', '130578', '87078148', '932484', '093779', '39393']

Related

How to populate multiple HTML DOM elements with local storage values

I want to display contents in the last <div> element when a click event occurs but now it only shows 1st 2 elements. Is there something I am not doing right somewhere?
Here is my code so far:
JS
const iname = document.getElementById("name");
const iemail = document.getElementById("email");
const iphone = document.getElementById("phone");
const submit = document.getElementById("submit");
const storage = document.getElementById("storage");
submit.onclick = function () {
const name = iname.value;
const email = iemail.value;
const phoneno = iphone.value;
if (name && email && phoneno) {
localStorage.setItem(name, "");
localStorage.setItem(email, "");
localStorage.setItem(phoneno, "");
location.reload();
}
};
for (let i = 0; i < localStorage.length; i++) {
const key = localStorage.key(i);
const value = localStorage.getItem(key);
storage.innerHTML += `Name : ${key}<br />Email : ${value}`;
}
localStorage.clear()
HTML
<p>Name</p>
<input id="name" autocomplete="off">
<p>Email</p>
<input id="email" autocomplete="off">
<p>Phone no</p>
<input id="phone" autocomplete="off">
<button id="submit">Let's go</button>
<div id="storage" class="box">
<h1>Is this correct?</h1></div>
I think you are setting the values in localstorage the wrong way.
The syntax for storing stuff in there is localstorage.setItem(keyName, keyValue).
And your code is setting the keyName argument to the value you are getting from the form and keyValue argument to an empty string; not what you need.
Make the following changes and you should be good to go (see comments):
submit.onclick = function () {
const name = iname.value;
const email = iemail.value;
const phoneno = iphone.value;
if (name && email && phoneno) {
// set local storage values
localStorage.setItem("name", name); // modified
localStorage.setItem("email", email); // modified
localStorage.setItem("phoneno", phoneno); // modified
location.reload();
}
console.log(localStorage); // new (maybe unnecessary)
};
for (let i = 0; i < localStorage.length; i++) {
const key = localStorage.key(i);
const value = localStorage.getItem(key);
storage.innerHTML += `${upFirst(key)}: ${value}<br>`; // modified
}
localStorage.clear();
/**
* new: making the first letter an upper case (for labels in the output div).
* See usage in 'for loop' above.
*/
function upFirst(stringValue) {
return stringValue.slice(0, 1).toUpperCase() + stringValue.slice(1);
}

Javascript loop array for form validation

I have a table form with some rows, that are controlled by user. Meaning they can add as more as they want. Let's pretend user requested 5 rows and i need to check if they all have values.
function validateForm() {
var lastRowInserted = $("#packageAdd tr:last input").attr("name"); // gives me "packageItemName5"
var lastCharRow = lastRowInserted.substr(lastRowInserted.length - 1); // gives me 5
var i;
for (i = 1; i <= lastCharRow; i++) {
var nameValidate[] = document.forms["packageForm"]["packageItemName"].value;
if(nameValidate[i].length<1){
alert('Please fill: '+nameValidate[i]);
return false;
}
}
}
How can i receive packageItemName1 to 5 values in a loop so then I can use to validate them. Want the loop to process this code
var nameValidate[] = document.forms["packageForm"]["packageItemName1"].value;
var nameValidate[] = document.forms["packageForm"]["packageItemName2"].value;
var nameValidate[] = document.forms["packageForm"]["packageItemName3"].value;
var nameValidate[] = document.forms["packageForm"]["packageItemName4"].value;
var nameValidate[] = document.forms["packageForm"]["packageItemName5"].value;
Like this
const validatePackageItems = () => {
const nameValidate = $("form[name=packageForm] input[name^=packageItemName]"); // all fields with name starting with packageItemName
const vals = nameValidate.map(function() { return this.value }).get(); // all values
const filled = vals.filter(val => val.trim() !== ""); // all values not empty
console.log("Filled", filled, "= ", filled.length, "filled of", vals.length)
return filled.length === vals.length
};
$("[name=packageForm]").on("submit",(e) => {
if (!validatePackageItems()) {
alert("not valid");
e.preventDefault();
}
})
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<form name="packageForm">
<input type="text" name="packageItemName1" value="one" /><br/>
<input type="text" name="packageItemName2" value="two" /><br/>
<input type="text" name="packageItemName3" value="" /><br/>
<input type="text" name="packageItemName4" value="four" /><br/>
<input type="submit">
</form>
You can use string interpolation to get the key dynamically:
for (let i = 1; i < 6; i++) {
const currentValue = document.forms.packageForm[`packageItemName${i}`]
console.log('current value:', currentValue)
}

JS RegExp capture all groups and pos for each match

Statement:
I am new to RegExp and trying to learn capture groups in javascripts
I am using https://regex101.com/r/COYhIc/1 for testing
see attached image for character pos column of each match by https://regex101.com
Objective:
I want to print all matches and groups at console (Done)
I want to print character position of each match [see image](remaining)
JSFIDDLE: https://jsfiddle.net/bababalcksheep/p28fmdk4/68/
JavaScript:
function parseQuery(query) {
var isRE = query.match(/^\/(.*)\/([a-z]*)$/);
if (isRE) {
try {
query = new RegExp(isRE[1], isRE[2]);
} catch (e) {}
}
return query;
}
var str = $('#str').val();
var regex = parseQuery($('#reg').val());
//
var result;
var match_no = 0;
var output = '';
while ((result = regex.exec(str)) !== null) {
match_no++;
output += `\nMatch ${match_no}\n`;
output += `Full Match, ${ result[0]} , Pos\n`;
for (i = 1; i < result.length; i++) {
output += `Group ${i}, ${ result[i]} , Pos\n`;
}
}
console.log(output);
In your output field use index and lastIndex. exec returns an object with a index property.
output += `Full Match, ${ result[0]} , Pos ${result.index} - ${regex.lastIndex}\n `;
Update for the groups:
I have used a small logic to get the indices:
var m = new RegExp(result[i]);
output += `Group ${i}, ${ result[i]}, Pos ${$('#str').val().match(m).index} - ${regex.lastIndex} \n`;
function parseQuery(query) {
var isRE = query.match(/^\/(.*)\/([a-z]*)$/);
if (isRE) {
try {
query = new RegExp(isRE[1], isRE[2]);
} catch (e) {}
}
return query;
}
var str = $('#str').val();
var regex = parseQuery($('#reg').val());
//
var result;
var match_no = 0;
var output = '';
while ((result = regex.exec(str)) !== null) {
match_no++;
output += `\nMatch ${match_no}\n`;
output += `Full Match, ${ result[0]} , Pos ${result.index} - ${regex.lastIndex}\n `;
for (i = 1; i < result.length; i++) {
var m = new RegExp(result[i]);
output += `Group ${i}, ${ result[i]}, Pos ${$('#str').val().match(m).index} - ${regex.lastIndex} \n`;
}
}
console.log(output);
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div class="container">
<div class="form-group">
<label for="str">String:</label>
<input type="text" class="form-control" id="str" value="source=100, delta=2, source=2121, delta=5">
</div>
<div class="form-group">
<label for="regex">Regex:</label>
<input type="text" class="form-control" id="reg" value="/(source=(\d+))/g">
</div>
<div id="result">
</div>
</div>
FIDDLE
According to docs RegExp.exec, you can retrieve it using index property. So I would add this line into your snippet to retrieve column position for your full match:
`${result.index}-${result.index + result[0].length}`
For subgroups, JS doesn't retrieve index, so a workaround can be achieved using indexOf:
const initialSubGroupIndex = str.indexOf(result[i], result.index);
`${initialSubGroupIndex}-${initialSubGroupIndex + result[i].length}`

How do you remove the beginning comma from a 2d array in javascript?

Okay I realize their is no such thing as a 2d array in javascript, but arrays can contain arrays, so its like a 2d array. Anyway I have a 2d array and it spits out a comma in the new line. I was wondering how do you remove it?
Here is my HTML
<form>
<h1>Please enter data</h1>
<input id="names" type="text" placeholder="Name" />
<input id="zipcodes" type="text" placeholder="Zip code" />
<input type="button" value="Save" onclick="insertData()" /> <br />
<input type="button" value="Display" onclick="displayData()" />
</form>
<div id="display"></div>
And my JavaScript
var namePlusZip = [[]];
var nameInput = document.getElementById("names");
var zipInput = document.getElementById("zipcodes");
var displayBox = document.getElementById("display");
function insertData() {
namePlusZip.push([nameInput.value, zipInput.value]);
delete namePlusZip[0];
nameInput.value = "";
zipInput.value = "";
}
function displayData(){
displayBox.innerHTML = "";
for (var i=0, l=namePlusZip.length; i<l; i++){
if (namePlusZip[i] instanceof Array){
namePlusZip[i] = namePlusZip[i].join(", ") + "</br>";
}
}
displayBox.innerHTML += "Names and zip codes: " + namePlusZip;
}
And here is the output.
// Names and zip codes:
// ,bobby, 12345
// ,tammy, 45677
// ,cindy, 34512
Notice the beginning comma. How do you get rid of it?
Instead of display the array string you can use join('').
Code:
displayBox.innerHTML += "Names and zip codes: " + namePlusZip.join('');
Demo: http://jsfiddle.net/0n9ryc3h/
If you declare your initial array like this:
var namePlusZip = [[]];
and after that push a new array there:
namePlusZip.push('one', 'two')
your array will look like this:
[[], ['one', 'two']]
If you paste in your console line:
[[], ['one', 'two']].join(',')
You will get this:
",one,two"
You don't have to declare array like [[]], just [] is enough
Also, I think your function is a bit wrong. Try this:
function displayData(){
displayBox.innerHTML = "";
var output = ''
for (var i=0, l=namePlusZip.length; i<l; i++){
if (namePlusZip[i] instanceof Array){
console.log(namePlusZip[i]);
var k = namePlusZip[i];
t = k.join(',')
console.log(t);
output += t + "</br>";
}
}
displayBox.innerHTML += "Names and zip codes: " + output;
}

Using for loop to generate text boxes

I want to be able to enter a number into a text box and then on a button click generate that number of text boxes in another div tag and automatically assign the id
Something like this but not sure how to generate the text boxes and assign automatically assign the id
function textBox(selections) {
for (i=0; i < selections +1; i++) {
document.getElementById('divSelections').innerHTML = ("<form><input type="text" id="1" name=""><br></form>");
}
}
Try this one:
function textBox(selections){
selections = selections*1; // Convert to int
if( selections !== selections ) throw 'Invalid argument'; // Check NaN
var container = document.getElementById('divSelections'); //Cache container.
for(var i = 0; i <= selections; i++){
var tb = document.createElement('input');
tb.type = 'text';
tb.id = 'textBox_' + i; // Set id based on "i" value
container.appendChild(tb);
}
}
A simple approach, which allows for a number to be passed or for an input element to be used:
function appendInputs(num){
var target = document.getElementById('divSelections'),
form = document.createElement('form'),
input = document.createElement('input'),
tmp;
num = typeof num == 'undefined' ? parseInt(document.getElementById('number').value, 10) : num;
for (var i = 0; i < num; i++){
tmp = input.cloneNode();
tmp.id = 'input_' + (i+1);
tmp.name = '';
tmp.type = 'text';
tmp.placeholder = tmp.id;
form.appendChild(tmp);
}
target.appendChild(form);
}
Called by:
document.getElementById('create').addEventListener('click', function(e){
e.preventDefault();
appendInputs(); // no number passed in
});
JS Fiddle demo.
Called by:
document.getElementById('create').addEventListener('click', function(e){
e.preventDefault();
appendInputs(12);
});
JS Fiddle demo.
The above JavaScript is based on the following HTML:
<label>How many inputs to create:
<input id="number" type="number" value="1" min="0" step="1" max="100" />
</label>
<button id="create">Create inputs</button>
<div id="divSelections"></div>
See below code sample :
<asp:TextBox runat="server" ID="textNumber"></asp:TextBox>
<input type="button" value="Generate" onclick="textBox();" />
<div id="divSelections">
</div>
<script type="text/javascript">
function textBox() {
var number = parseInt(document.getElementById('<%=textNumber.ClientID%>').value);
for (var i = 0; i < number; i++) {
var existingSelection = document.getElementById('divSelections').innerHTML;
document.getElementById('divSelections').innerHTML = existingSelection + '<input type="text" id="text' + i + '" name=""><br>';
}
}
</script>
Note: Above code will generate the N number of textboxes based on the number provided in textbox.
It's not recommended to user innerHTML in a loop :
Use instead :
function textBox(selections) {
var html = '';
for (i=0; i < selections +1; i++) {
html += '<form><input type="text" id="'+i+'" name=""><br></form>';
}
document.getElementById('divSelections').innerHTML = html;
}
And be carefull with single and double quotes when you use strings
You have to change some code snippets while generating texboxes, Learn use of + concatenate operator, Check code below
function textBox(selections) {
for (var i=1; i <= selections; i++) {
document.getElementById('divSelections').innerHTML += '<input type="text" id="MytxBox' + i + '" name=""><br/>';
}
}
textBox(4); //Call function
JS Fiddle
Some points to taken care of:
1) In for loop declare i with var i
2) your selection + 1 isn't good practice at all, you can always deal with <= and < according to loop's staring variable value
3) += is to append your new HTML to existing HTML.
ID should be generate manually.
var inputName = 'divSelections_' + 'text';
for (i=0; i < selections +1; i++) {
document.getElementById('divSelections').innerHTML = ("<input type='text' id= " + (inputName+i) + " name=><br>");
}
edit : code formated
Instead of using innerHTML, I would suggest you to have the below structure
HTML:
<input type="text" id="id1" />
<button id="but" onclick="addTextBox(this)">click</button>
<div id="divsection"></div>
JS:
function addTextBox(ops) {
var no = document.getElementById('id1').value;
for (var i = 0; i < Number(no); i++) {
var text = document.createElement('input'); //create input tag
text.type = "text"; //mention the type of input
text.id = "input" + i; //add id to that tag
document.getElementById('divsection').appendChild(text); //append it
}
}
JSFiddle

Categories

Resources