javascript loop form values by name then element id - javascript

I have loop going though form values, it is working fine throwing out the values based on the input name. But I would also like to be able to target by specific element id.
This is an example form:
_inputFields: function() {
var rows = [];
for(var i = 1; i <= 12; i++) {
var placeHolder = 'Intro text line ' + i;
var inputID = 'inputIntroText ' + i;
rows.push(<input type="text" className="form-control input-size-lg" name="formInput" id="inputText" placeholder={placeHolder}/>);
rows.push(<input type="text" className="form-control input-size-lg" name="formInput" id="inputTime" placeholder={placeHolder}/>);
}
So I can loop through and grab everything by name i.e. 'formInput' but how can I then grab formInput[inputText] and formInput[inputTime]?
This is my current loop through the values :
// gather form input
var elem = document.getElementsByName('formInput');
console.log(elem);
// Build the object
var obj = {
"DataObject": {
"user": {
"-name": "username"
},
"contentFile": {
"-filename": "Breaking_News",
"lock": {
"-fileIsBeingEdited": "false"
},
"content": {
"line": []
}
}
}
};
var line = obj.DataObject.contentFile.content.line;
for (var i = 0; i < elem.length; i++) {
if (elem[i].value != '') {
line.push({
"-index": i,
"-text": elem[i]['inputText'].value,
"-time": elem[i]['inputTime'].value
});
}
};
If I try:
"-text": elem[i]['inputText'].value,
"-time": elem[i]['inputTime'].value
I get the error: Cannot read property 'value' of undefined

This errors because elem[i]['inputText'] is undefined. This is because you are trying to lookup the inputText property of the element, which doesn't exist.
elem is an array, so I'd recommend using something like filter.
"-text": elem.filter(function(item) {
return item.id === 'inputText';
})[0].value;
Also, you should remove the for loop or you will get a duplicate line.
function getElementById(elems, id){
return elems.filter(function(item) {
return item.id === id;
})[0];
}
var line = obj.DataObject.contentFile.content.line;
line.push({
"-text": getElementById(elem, 'inputText').value,
"-time": getElementById(elem, 'inputTime').value
});
Here's an example jsfiddle.

You can use elem[i].id:
var line = obj.DataObject.contentFile.content.line;
for (var i = 0; i < elem.length; i++) {
if (elem[i].value != '') {
line.push({
"-index": i,
"-text": elem[i].id
// Since you are looping through the inputs, you will get the `inputTime` in the 2nd iteration.
});
}
};

Related

Problem with function reading all attributes of given node

// function to read all attributes
function get_attributes(source_node) { // source of attributes
var i, attribute, size, tab = [];
attribute = { name: "", value: "" } // new type
size = source_node.attributes.length; // reading size
for (i = 0; i < size; i++) {
attribute.name = source_node.attributes[i].name;
attribute.value = source_node.attributes[i].value;
tab[i] = attribute; //putting attribute into table
alert(tab[i].name + " - " + tab[i].value);
}
return tab; //returning filled table
}
Problem is, table (tab) consists only last red parameter :(
Anyone?
Source_node can be anything. ie "document.body"
it works if declared inside loop
...
for (i = 0; i < size; i++) {
VAR attribute =[];
attribute.name = source_node.attributes[i].name;
attribute.value = source_node.attributes[i].value;
tab[i] = attribute; //putting attribute into table
}
....

Javascript Substring replace with JQuerys contains selector

I'm trying to find a specific row in a column of an HTML table and replace an occurrence of a specific string with a given value.
I tried to use JQuery's .html but it just replaces everything in the row with the given value. A .text().replace() returned me false.
Here's my code:
function ReplaceCellContent(find, replace)
{
//$(".export tr td:nth-child(4):contains('" + find + "')").html(function (index, oldHtml) {
// return oldHtml.replace(find, replace);
//});
$(".export tr td:nth-child(4):contains('" + find + "')").text($(this).text().replace(find, replace));
//$(".export tr td:nth-child(4):contains('" + find + "')").html(replace);
}
$('.export tr td:nth-child(4)').each(function () {
var field = $(this).text();
var splitter = field.split(':');
if (splitter[2] === undefined) {
return true;
} else {
var splitter2 = splitter[2].split(',');
}
if (splitter2[0] === undefined) {
return true;
} else {
$.post(appPath + 'api/list/', {action: 'getPW', pw: splitter2[0]})
.done(function (result) {
ReplaceCellContent(splitter2[0], result);
});
}
});
I'm iterating through every row of the column 4 and extracting the right string. This is going through an AJAX post call to my function which returns the new string which I want to replace it with.
splitter2[0] // old value
result // new value
I hope someone could help me. I'm not that deep into JS/JQuery.
findSmith findJill findJohn
var classes = document.getElementsByClassName("classes");
var replaceCellContent = (find, replace) => {
for (var i = 0; i < classes.length; i++) {
if (classes[i].innerText.includes(find)) {
classes[i].innerText = classes[i].innerText.replace(find, replace);
}
}
}
this replaces all "fill" occurrences to "look".
I love to use vanilla JS, I'm not really a fan of JQuery but this surely should work on your code.
Do like this :
var tds = $("td");
for( var i = 0; i < tds.length ; i++){
if ( $(tds[i]).text().includes("abc") ){
var replacetext = $(tds[i]).text().replace("abc", "test");
$(tds[i]).text(replacetext);
}
}
Say give all your table rows a class name of "trClasses"
var rows = document.getElementsByClassName("trClasses");
for (var I = 0; I < rows.length; I++) {
rows.innerText.replace("yourText");
}
The innerText property would return the text in your HTML tag.
I'm a newbie too, but this should work. Happy Coding!

Checking for a value within select box while looping

I'm looping over an Ajax result and populating the JSON in a select box, but not every JSON result is unique, some contain the same value.
I would like to check if there is already a value contained within the select box as the loop iterates, and if a value is the same, not to print it again, but for some reason my if check isn't working?
for (var i = 0; i < result.length; i++) {
var JsonResults = result[i];
var sourcename = JsonResults.Source.DataSourceName;
if ($('.SelectBox').find('option').text != sourcename) {
$('.SelectBox').append('<option>' + sourcename + '</option>');
}
}
The text() is a method, so it needs parentheses, and it returns text of all <option> concatenated. There are better ways to do this, but an approach similar to yours can be by using a variable to save all the added text, so we can check this variable instead of having to check in the <option> elements:
var result = ["first", "second", "first", "third", "second"];
var options = {};
for (var i = 0; i < result.length; i++) {
var JsonResults = result[i];
var sourcename = JsonResults; //JsonResults.Source.DataSourceName;
if (!options[sourcename]) {
$('.SelectBox').append('<option>' + sourcename + '</option>');
options[sourcename] = true;
}
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<select class="SelectBox"></select>
Note: I only used var sourcename = JsonResults; for the demo. Use your original line instead.
.text is a function, so you have to call it to get back the text in the option
for (var i = 0; i < result.length; i++) {
var JsonResults = result[i];
var sourcename = JsonResults.Source.DataSourceName;
if ($('.SelectBox').find('option').text() != sourcename) {
$('.SelectBox').append('<option>' + sourcename + '</option>');
}
}
For one thing, the jQuery method is .text() - it's not a static property. For another, your .find will give you the combined text of every <option>, which isn't what you want.
Try deduping the object before populating the HTML:
const sourceNames = results.map(result => result.Source.DataSourceName);
const dedupedSourceNames = sourceNames.map((sourceName, i) => sourceNames.lastIndexOf(sourceName) === i);
dedupedSourceNames.forEach(sourceName => {
$('.SelectBox').append('<option>' + sourceName + '</option>');
});

How to create key => values array in a collection object in Javascript

I've this HTML table:
<table class="table table-condensed">
<thead>
<tr>
<th><input type="checkbox" id="toggleCheckboxSelFabricante" name="toggleCheckboxSelFabricante"></th>
<th>Fabricante</th>
</tr>
</thead>
<tbody id="selFabricanteBody">
<tr>
<td><input type="checkbox" name="selChkFabricante" id="selChkFabricante3" value="3"></td>
<td>Eos est ipsam.</td>
</tr>
</tbody>
</table>
I need to create a key => value for manufacturerColl var where id is the value of each checked checkbox (first td on the table) and name is the text on the second column but don't know how to. This is what I've in my code:
var checkedModelBranch = $("#parMarcaModeloFabricanteBody").find("input[type='checkbox']:checked"),
checkedManufacturers = $("#selFabricanteBody").find("input[type='checkbox']:checked"),
manufacturerColl = [],
modelBranchManufacturerCollection;
for (var j = 0; j < checkedManufacturers.length; j++) {
manufacturerColl.push(checkedManufacturers[j].value);
}
for (var i = 0; i < checkedModelBranch.length; i++) {
modelBranchManufacturerCollection = addNewRelationModelBranchManufacturer(checkedModelBranch[i].value, manufacturerColl);
if (modelBranchManufacturerCollection) {
for (var k = 0; k < modelBranchManufacturerCollection.manufacturerKeyCollection.length; k++) {
$("#parMarcaModeloFabricanteBody td#" + checkedModelBranch[i].value).html(modelBranchManufacturerCollection.manufacturerKeyCollection[k] + '<br/>');
}
}
}
What I need in others words is for each manufacturerColl have and id => name, ex:
manufacturerColl[] = {
id: someId,
name: someName
};
And I'm not sure but maybe this could work:
// move foreach selected checkbox and get the needed
for (var j = 0; j < checkedManufacturers.length; j++) {
manufacturerColl.push({
id: checkedManufacturers[j].value,
name: "" // how do I get the value on the second column?
});
}
Which is the right way to do this? How do I get the value on the second column on each iteration?
Approach
I don't know if this is complete right but is what I've done and it's buggy. See the code:
var checkedModelBranch = $("#parMarcaModeloFabricanteBody").find("input[type='checkbox']:checked"),
checkedManufacturers = $("#selFabricanteBody").find("input[type='checkbox']:checked"),
// I added this var to get all the names
checkedManufacturersName = $("#selFabricanteBody").find("input[type='checkbox']:checked").parent().next('td').text(),
manufacturerColl = [],
modelBranchManufacturerCollection;
for (var j = 0; j < checkedManufacturers.length; j++) {
manufacturerColl.push({
id: checkedManufacturers[j].value,
// Here I'm tying to put the entire name but get only the first character
name: checkedManufacturersName[j]
});
}
for (var i = 0; i < checkedModelBranch.length; i++) {
modelBranchManufacturerCollection = addNewRelationModelBranchManufacturer(checkedModelBranch[i].value, manufacturerColl);
if (modelBranchManufacturerCollection) {
//$("#parMarcaModeloFabricanteBody td#" + checkedModelBranch[i].value).siblings().attr("rowspan", modelBranchManufacturerCollection.manufacturerKeyCollection.length);
for (var k = 0; k < modelBranchManufacturerCollection.manufacturerKeyCollection.length; k++) {
// then I render the name attribute from the collection
$("#parMarcaModeloFabricanteBody td#" + checkedModelBranch[i].value).append((modelBranchManufacturerCollection.manufacturerKeyCollection)[k].name + '<br/>');
}
}
}
Why I'm inserting/getting the first character only and not the complete string?
//Since your input and text are wrapped in td elements
In the code:
var checked = $('#selFabricanteBody').find('input[type="checkbox"]:checked');
var arr = [], j = checked.length, item;
while(j--) {
item = list[j];
//gets the text from the next child, assumes its the text
//if the text is before checkbox, use previousSibling
arr.push({id: item.value, name: item.parentNode.nextSibling.nodeValue});
}
This is what I use to create an object, for sending to a controller method that is looking for a class/model as a parameter:
function ExtractModel(array) {
var modelString = '';
var model = {};
//var array = arrayString.split('&');
var isObjectModel = $.isPlainObject(array);
if (!isObjectModel) {
$(array).each(function (index, element) {
var typeId = element.split('=')[0];
var val = element.split('=')[1];
if (element == null) { } else {
model[typeId] = (val);
}
});
} else {
model = array;
}
return model;
};
So, with this, I am taking a url parameter string and creating an object from it; the parameter string is generated from serializing the form. The "model" automatically creates the property that is represented by "typeId"; if "typeId" = "hello", then a new property or object item will be created, named "hello" (model.hello will get you a value). You can use this same logic to loop through the elements on your page to populate the object with multiples. Make sure to set your variable "modelBranchManufacturerCollection" equal to {}, and to then set the index of where to insert a new one.
This should do what you want:
var ids = [1, 2, 3, 4, 5, 6]
var names = ['a', 'b', 'c', 'd', 'e', 'f']
var mainObj = {};
$(ids).each(function (index, element) {
var miniObj = {};
miniObj['id'] = ids[index];
miniObj['name'] = names[index];
mainObj[index] = miniObj;
});
returns 6 items of id and name.

Filter a child picklist in CRM 2011

I'm trying to convert javascript code from CRM 4.0 to CRM 2011.
I'm having problems with a picklist filter.
My function is on the onchange of the parent picklist. It works the first time but the second it erase everything from my child picklist.
This is the part where I suppose to reset the picklist
if(!oSubPicklist.originalPicklistValues)
{
oSubPicklist.originalPicklistValues = oSubPicklist.getOptions();
}
else
{
oSubPicklist.getOptions = oSubPicklist.originalPicklistValues;
oSubPicklist.setOptions = oSubPicklist.originalPicklistValues;
}
And this is the part where i remove all the option not related:
oTempArray is an array with the options that i want to keep. If a check the "oSubPicklist.getOptions.length" the value is the same that my original picklist.
for (var i=oSubPicklist.getOptions.length; i >= 0;i--)
{
if(oTempArray[i] != true)
{
Xrm.Page.getControl("new_product").removeOption(i);
}
}
Ideas?
Edit: I solved declaring a global var with the originalPickList in the onLoad event and:
oSubPicklist.clearOptions();
for (var i=0; i< oSubPicklist.originalPicklistValues.length; i++)
{
for (var j=0; j< oDesiredOptions.length; j++)
{
if (i == oDesiredOptions[j])
{oSubPicklist.addOption(oSubPicklist.originalPicklistValues[i]);}
}
}
Your code is not very clear to me: May be you could paste all your function code for better understanding but:
This is how you get the options from PickList in CRM 2011
var myOptionSet = Xrm.Page.ui.controls.get("new_product") //get Control
var optionsSet = myOptionSet .getAttribute().getOptions(); //get Options
preferredTimeOptionSet.clearOptions(); //Clear all options
//Create a new Option
var opt1 = new Option();
opt1.text = "one";
opt1.value = 1;
//Add Option
myOptionSet.addOption(opt1);
//Remove Option
myOptionSet.removeOption(1);
Good Example here
Here is another way to do Parent/Child picklists:
function dynamicDropdown(parent, child) {
filterPicklist(parent, child);
}
function parentListFilter(parent, id) {
var filter = "";
if (getParentCode(parent) != "") {
filter = getParentCode(parent);
} else {
// No [ ] match
}
return filter;
}
function filterPicklist(parent, child) {
var parentList = Xrm.Page.getAttribute(parent).getValue();
var childListControlAttrib = Xrm.Page.getAttribute(child);
var childListOptions = childListControlAttrib.getOptions();
var childListControl = Xrm.Page.getControl(child);
var codeToFilterListOn = parentListFilter(parent, parentList);
if (codeToFilterListOn != "") {
childListControl.clearOptions();
for (var optionIndex in childListOptions) {
var option = childListOptions[optionIndex];
// Ignore xx and check for Match
if (option.text.substring(0, 2) != "xx" && option.text.indexOf(codeToFilterListOn) > -1) {
childListControl.addOption(option);
}
}
} else {
// Didn't match, show all?
}
}
function getParentCode(parent) {
//Get Parent Code Dynamically from inside [ ]
var filter = "";
var parentValue = Xrm.Page.getAttribute(parent).getText();
if (parentValue && parentValue.indexOf("]") > -1) {
var parentCode = parentValue.substring(parentValue.indexOf("[") + 1, parentValue.indexOf("]"));
if (parentCode) {
filter = parentCode + " | ";
} else {}
}
return filter;
}
See more here: Parent/Child

Categories