[Code]
$.ajax
({
'method': 'GET',
'source': '/bpv-registratie/periods/show_period_list_by_year.html',
'charge': function ()
{
},
'finish': function (xmlHttp)
{
var options = new Array();
var response = eval('(' + xmlHttp.responseText + ')');
var child = document.createElement('option');
child.setAttribute('value', 'none');
child.setAttribute('checked', 'checked');
child.innerHTML = ' ';
options.push(child);
for (var c = 0; c < response.length; c++)
{
var child = document.createElement('option');
child.setAttribute('value', response.data[c].periode_id);
child.innerHTML = response.data[c].periode_naam +
' (' +
response.data[c].periode_startdatum +
' t/m ' +
response.data[c].periode_einddatum +
' )';
options.push(child);
}
for (var a = 0; a < obj.childNodes.length; a++)
{
var e = obj.childNodes[a].getElementsByTagName("select");
for (var f = 0; f < e.length; f++)
{
e[f].length=0;
for (var o = 0; o < options.length; o++)
{
e[f].appendChild(options[o]);
}
}
alert('test');
}
}
});
[Problem]
Running the code above with the alert, it shows that all the select boxes do get filled with the options I want them to. However as soon as it starts filling the next select box, the previous is being cleared again.
Does anyone know why?
[Situation]
I have a bunch of select boxes generated from about the same code. These represent a class a person can be in. The class should be selected from the selectbox. However if the teacher wishes to change the person to a different period, that would most likely mean that there are different classes available in that period so what I'm trying to do is fill the select boxes with the classes from the new period.
I think your problem is that a single option object can only be in one <select> at a time. Your first trip through the loop fills the first select, then your second trip through the loop moves the options from the first <select> to the second. Rinse and repeat until your final <select> ends up with all the options.
The solution is to create the options when you're about to add them to the <select>. Your first loop should just build an array to hold the values and labels, then expand that simple data to option DOM elements and hand them over to the <select>. This will create a unique set of option objects for each <select>.
Here's a simple example that you can play with to see what's going on:
http://jsfiddle.net/ambiguous/9WuQC/
I'll include the fiddle inline for future reference; the HTML:
<select id="a"></select>
<select id="b"></select>
<button id="c">fill first</button>
<button id="d">fill second</button>
And JavaScript:
var options = [ ];
var option;
for(var i = 0; i < 10; ++i) {
option = document.createElement('option');
option.setAttribute('value', i);
option.innerHTML = i;
options.push(option);
}
$('#c').click(function() {
var s = document.getElementById('a');
for(var i = 0; i < options.length; ++i)
s.appendChild(options[i]);
});
$('#d').click(function() {
var s = document.getElementById('b');
for(var i = 0; i < options.length; ++i)
s.appendChild(options[i]);
});
I'm not sure what obj actually is, but in my mind, this is what is happening (denoted by the comments):
//loop round all the child nodes of obj (not just immediate children)
for (var a = 0; a < obj.childNodes.length; a++)
{
//get all <select> elements under the current child (a) of obj
var e = obj.childNodes[a].getElementsByTagName("select");
//loop round our selects under the current child node
for (var f = 0; f < e.length; f++)
{
e[f].length=0;
for (var o = 0; o < options.length; o++)
{
e[f].appendChild(options[o]);
}
}
alert('test');
}
The comment 'not just immediate' is pertintent here. Say you have a structure
<div id="a">
<div id="b">
<div id="c">
<select id="d"></select>
</div>
</div>
</div>
When you loop through the children of 'a' you get ALL the children, i.e. b,c,d. Next time around your child iteration you are looking at 'b' itself, so you get 'c' and 'd'.
In each of these loops, you populate the select box.
The short answer is that you have probably made a false assumption about the childNodes property.
Related
working on from my previous Q
http://stackoverflow.com/questions/33550384/check-value-in-table-row-column
val = 2
get table.row[where val = data-uid]
check next row
if table.rows[data-uid = val] continue until it is not the same, when value is different pass back
var newVal = ?
this all works but only for the first button click. on the second button click the table holds the value from the previous search as opposed to checking all the values in the jquery datatable. I tried reseting the filters but this didnt work...
t.fnResetAllFilters(false);
//t.fnResetAllFilters();
// t.fnFilter('');
so basically the first time round time round
var elements = document.getElementsByTagName('tr');
var elementsLength = elements.length;
elements.length returns a value ofd 10. but because currentElement returns 4 results the next time round elements.length only contains 4 results
loop1:
for (var i = 0; i < elements.length; i++)
{
var currentElement = elements[i].getAttribute('data-uid');
loop2:
for (var j = i + 1; j < elements.length; j++)
{
var nextElement = elements[j].getAttribute('data-uid');
if (currentElement !== nextElement)
{
rowId = elements[j].getAttribute('data-uid');
break loop1;
//return;
}
}
}
var split = $('.split-locations').text().split('\n');
for (var i = 0; i < split.length; i++) {
$('.split-locations').append("<pre>"+split[i]+"</pre>");
}
<div class="split-location">
Singapore
USA
Aussie
</div>
On profile, the user type with enter for each address, but the problem is when it is saved, the addresses would be displayed on the webpage as:
Singapore USA Aussie
<pre>Singapore</pre>
<pre>USA</pre>
<pre>Aussie</pre>
I am not sure why the text (Singapore USA Aussie) is still there. Only wanted to display:
<pre>Singapore</pre>
<pre>USA</pre>
<pre>Aussie</pre>
How to remove the first line before <pre> bunch? Or how to replace text with pre bunch?
Update
One more thing: how to print first array outside loop because need to display first one outside loop and then put the rest of array inside accordion?
Here the code is: for you to understand what I am trying to do. see the comment.
var location = $('.split-locations');
var split = $('.split-locations').text().split('\n');
location.empty();
//need to print first location
location.append('<div class="accordion-location">');
for (var i = 0; i < split.length; i++) {
//print remaining location after minus first location
location.append("<pre>"+split[i]+"</pre>");
}
location.append('</div>');
});
You need to empty the container element before appending the pre nodes. Try this.
var split = $('.split-locations').text().split('\n');
$('.split-locations').empty();
for (var i = 0; i < split.length; i++) {
$('.split-locations').append("<pre>"+split[i]+"</pre>");
}
You need to clear out the location:
var split = $('.split-locations').text().split('\n');
$('.split-locations').empty();
for (var i = 0; i < split.length; i++) {
$('.split-locations').append("<pre>"+split[i]+"</pre>");
}
Update:
var $el = $('<div class="accordion-location"></div>');
for (var i = 0; i < split.length; i++) {
$el.append("<pre>"+split[i]+"</pre>");
}
location.append($el);
I'm trying to update the options of ALL select lists on a page and implemented a solution found on Get list of all `input` objects using JavaScript, without accessing a `form` object and other pages.
This works to an extent but only the select lists which occur AFTER the one which is triggering the javascript are updated whereas I need them ALL done, regardless of their position relative to the triggering select.
Here's a simplified version of what I have:
function chooseBon(id, value) {
var bonbonsAmount = 12;
var bonbonsCurrent = 0;
var bonbonsCount = 4;
var inputs, index;
// get all the select lists
inputs = document.getElementsByTagName('select');
// loop through all the lists
for (index = 0; index < inputs.length; ++index) {
// First disable all options
for (j = 0; j<=bonbonsAmount; ++j) {
inputs[index].options[j].disabled="disabled";
}
// Then re-enable the ones we still need
for (j = 0; j<=(bonbonsAmount - bonbonsCurrent); ++j) {
inputs[index].options[j].disabled="";
}
// add up the no of chocs selected so we know how many options to re-enabled above
bonbonsCurrent += inputs[index].selectedIndex;
}
I'm an admitted newbie and am adapting a script from one ecommerce platform for another so am hamstrung in certain areas so feel free to make other suggestions.
here is one of possible solutions and the fiddle:
function chooseBon() {
var bonbonsAmount = 12;
var bonbonsCurrent = 0;
var bonbonsRemaining; //max. is bonbonsAmount
var inputs, i, j;
inputs = document.getElementsByTagName('select');
for (i = 0; i < inputs.length; i++) {
bonbonsCurrent += parseInt(inputs[i].value, 10);
}
bonbonsRemaining = bonbonsAmount - bonbonsCurrent;
for (i = 0; i < inputs.length; i++) {
for (j = 0; j <= bonbonsAmount; j++) {
inputs[i].options[j].disabled = (j < bonbonsRemaining + parseInt(inputs[i].value, 10) + 1) ? false : true;
}
}
}
Can someone help what's the javascript equivalent of below jquery line.
$("#abc option[value='1']").text();
abc is the id of selectbox
var options = document.getElementById("abc").options;
for (var i = 0, j = options.length; i < j; i++) {
if (options[i].value == "1") {
alert(options[i].text);
}
}
The value and text attributes are available on the HTMLOptionElement per DOM Level 2.
(demo)
UPDATE
Updated demo with combined text, cf. comments:
var options = document.getElementById("abc").options,
text = "";
for (var i = 0, j = options.length; i < j; i++) {
if (options[i].value == "1") {
text += options[i].text;
}
}
This would be 100% equivalent to the selector:
var options = document.getElementById('abc').getElementsByTagName('option'),
text = "";
for(var i = 0, l = options.length; i < l; i++) {
var option = options[i];
if(option.value === '1') {
text += option.text;
}
}
Or if querySelectorAll is available:
var options = document.querySelectorAll('#abc option[value="1"]'),
text = "";
for(var i = 0, l = options.length; i < l; i++) {
text += options[i].text;
}
That said, you can make improvements depending on the HTML structure (e.g. if #abc is the select element etc).
In modern browsers it can be:
var option = document.querySelector('#abc option[value="1"]').textContent
The statement doesn't make sense. It gets the text from an option, and then just throws it away. I assume that you want to do something with the text, like assigning it to a variable.
// A variable for the result
var text = null;
// Get the options from the select element
var options = document.getElementById('abc').options;
// Find the option with the value "1"
for (var i = 0; i < options.length; i++) {
if (options[i].value == '1') {
// Get the text from the option
text = options[i].text;
// Exit from the loop
break;
}
}
Note: The original code would get the text from all options with the specified value, but this code only gets the text from the first option found. Having more than one option with the same value is pretty useless, so that feature of the original code is most likely unintended.
This Will Work.
document.querySelector(".producer option[value='1']").text;
I have a couple of lines of code in JQuery:
var central = $('#townid option:contains("Central")');
if (central.length){
central.insertAfter('select option:first-child');
}
How can I rewrite it without using JQuery library just with JavaScript?
A correct translation would be something like:
var selects = document.getElementsByTagName('select'),
options = document.getElementById('townid').getElementsByTagName('option'),
options = Array.prototype.slice.call(options), //2 lines only for readability
tmp = document.createDocumentFragment();
for(var i = 0, l = options.length; i < l; i++) {
var option = options[i],
text = option.innerText || option.textContent;
if(text.indexOf('Central') > -1) {
tmp.appendChild(option);
}
}
for(var i = 0, l = selects.length; i < l; i++) {
var select = selects[i],
opts = select.getElementsByTagName('option');
if(opts.length > 1) {
select.insertBefore(tmp.cloneNode(true), opts[1]);
}
else {
select.appendChild(tmp.cloneNode(true));
}
}
DEMO
This could be simplified a lot depending on the markup (and optimized depending on the browser (e.g. support for querySelectorAll)). E.g. if you know that there will always only be one option that contains "Central" and whether there exists only one select element or not.
Here is a stripped down version for one select element, known size of the list (i.e. > 1) and only one option that contains Central. So basically just reordering the option:
var options = document.getElementById('townid').getElementsByTagName('option');
for (var i = 0, l = options.length; i < l; i++) {
var option = options[i],
text = option.innerText || option.textContent;
if (text.indexOf('Central') > -1) {
if (i > 1) {
option.parentNode.insertBefore(option, options[1]);
}
break;
}
}
DEMO
Update:
If the option's text should be exactly Central, compare the text normally:
if(text === 'Central')