jQuery multiple parent() calls - javascript

I have this for loop that gets the id and text of parents elements:
for (var i = 1; i < parents_num; i++)
{
var prev_parent_text = jQuery(id).parent().parent().find('> .myclass').text();
var prev_parent_id = jQuery(id).parent('ul').parent('li').attr('id');
}
What I am trying to do is to increase the number of parent() by 2 in each loop:
For example,
for i = 1:
var prev_parent_text = jQuery(id).parent().parent().find('> .myclass').text();
var prev_parent_id = jQuery(id).parent('ul').parent('li').attr('id');
for i = 2:
var prev_parent_text = jQuery(id).parent().parent().parent().parent().find('> .myclass').text();
var prev_parent_id = jQuery(id).parent('ul').parent('li').parent('ul').parent('li').attr('id');
for i = 3:
var prev_parent_text = jQuery(id).parent().parent().parent().parent().parent().parent().find('> .myclass').text();
var prev_parent_id = jQuery(id).parent('ul').parent('li').parent('ul').parent('li').parent('ul').parent('li').attr('id');
and so on..
I have used the eq() function unsuccesfully:
var num = (i*2) - 2
var prev_parent_text = jQuery(id).parent().eq(num).find('> .myclass').text();
var prev_parent_id = jQuery(id).parent('ul').parent('li').eq(num).attr('id');
Thank you for any help

Keep a reference for each, and update the reference for each step:
var $id = jQuery(id);
var $li = jQuery(id);
for (var i = 1; i < parents_num; i++) {
$id = $id.parent().parent();
$li = $li.parent('ul').parent('li');
var prev_parent_text = $id.find('> .myclass').text();
var prev_parent_id = $li.attr('id');
}

You could add a custom jquery function for that, like this:
$.fn.nparent = function(n) {
var elem = $(this);
for (var i=0;i<n;i++) {
elem = elem.parent();
}
return elem;
}
And use it like:
var id = $('#element').nparents(4).attr('id');

Related

Javascript a TD click and get row cell data

I have this in Jquery all works:
$(document).ready(function() {
$("#checktable td:nth-child(1)").click(function(event){ // This line I need converted
event.preventDefault();
var $td = $(this).closest('tr').children('td'); //This line I need converted
var tid = $td.eq(0).text();
var tdate = $td.eq(1).text();
var tdescribe = $td.eq(2).text();
var wd = $td.eq(3).text();
var dep = $td.eq(4).text();
// ... more code
I need a similar thing in javascript, above only first td is clicked.
My javascript code so far:
function addRowHandlers() {
var table = document.getElementById("checktable2");
var rows = table.getElementsByTagName('tr');
var tid = '';
var tdate = '';
var tdescribe = '';
var wd = '';
var dep = '';
var tisclr = '';
for (var i = 1; i < rows.length; i++) {
rows[i].i = i;
rows[i].onclick = function() {
tid = table.rows[this.i].cells[0].innerText;
tdate = table.rows[this.i].cells[1].innerHTML;
tdescribe = table.rows[this.i].cells[2].innerHTML;
wd = table.rows[this.i].cells[3].innerHTML;
dep = table.rows[this.i].cells[4].innerHTML;
// ... etc more code
The javascript works but any td can be clicked, I am after only:
The first td clicked
Then get parent row
Then all child td's
I have been over dozens of StackOverflow posts and other sites as well... Thanks
And how do I add the event.preventDefault() to regular JS in such a case.
You'd bind the handler to the first .cell.
rows[i].cells[0].onclick = function () {
And then in the handler, access the .parentNode of this to get the row.
And since you're not closing over any variables except those in the function itself (and outside that function, of course), I'd just use a single handler instead of recreating it in the loop.
function addRowHandlers() {
var table = document.getElementById("checktable2");
var rows = table.getElementsByTagName('tr');
var tid = '';
var tdate = '';
var tdescribe = '';
var wd = '';
var dep = '';
var tisclr = '';
for (var i = 1; i < rows.length; i++) {
rows[i].i = i;
rows[i].cells[0].onclick = handler;
}
function handler() {
var row = this.parentNode;
tid = this.innerText;
tdate = row.cells[1].innerHTML;
tdescribe = row.cells[2].innerHTML;
wd = row.cells[3].innerHTML;
dep = row.cells[4].innerHTML;
// etc more code
}
}
I'd probably use a loop to get the desired content too. Maybe like this:
function handler() {
var row = this.parentNode;
var props = ["tid", "tdate", "tdescribe", "wd", "dep"];
var content = props.reduce(function(obj, key, i) {
obj[key] = row.cells[i][i ? "innerHTML" : "innerText"];
return obj;
}, {});
// etc more code
}
Now instead of variables, you have properties of the content object.

I just want to put some texts between tags using appendchild methods with Javascript

This code below is a javascript code to change texts and background properties from the body tag at the same time when the browser is clicked. I've just followed rules in w3school.com, actually, I'm doing the same as the examples do, but mine won't work and I've failed to find my fault. plz, help me.
var helloDiv = document.createElement("div");
var helloText = document.createTextNode("hi.");
helloDiv.appendChild(helloText);
var bodyntext = document.getElementsByTagName("body").appendChild(helloDiv);
var complementary = new Array();
var j = 0;
window.onclick = function(){
var background_color;
var body = document.getElementsByTagName("body")[0];
// var color = new Array();
var result = null;
var number = Math.round(Math.random()*0xFFFFFF);
for(var i = 0; i > 3; i++)
{
complementary[i] = (255-(number.slice(j,j+1).toString(10))).toString(16);
j = j + 2;
}
var clnumber = (complementary[0]+complementary[1]+complementary[2]).toString(16);
body.style.backgroundColor = "#"+ number.toString();
bodyntext.style.color = "#"+ clnumber.toString();
}
Here's your problem
var bodyntext = document.getElementsByTagName("body").appendChild(helloDiv);
Please note that the javascript functions that have plural names often return arrays which is the case here
document.getElementsByTagName("body") returns an array and you are trying to perform an invalid action, that is append child, to this array. You need to access an element using index and then perform this action.
so using
var bodyntext = document.getElementsByTagName("body")[0].appendChild(helloDiv); should fix your problem.
Use document.getElementsByTagName("body")[0] to achieve expected result, as getElementsByTagName() method returns a collection of all elements in the document with the specified tag name, as a NodeList object.
var helloDiv = document.createElement("div");
var helloText = document.createTextNode("hi.");
helloDiv.appendChild(helloText);
var bodyntext = document.getElementsByTagName("body")[0].appendChild(helloDiv);
var complementary = new Array();
var j = 0;
window.onclick = function(){
var background_color;
var body = document.getElementsByTagName("body")[0];
// var color = new Array();
var result = null;
var number = Math.round(Math.random()*0xFFFFFF);
for(var i = 0; i > 3; i++)
{
complementary[i] = (255-(number.slice(j,j+1).toString(10))).toString(16);
j = j + 2;
}
var clnumber = (complementary[0]+complementary[1]+complementary[2]).toString(16);
body.style.backgroundColor = "#"+ number.toString();
bodyntext.style.color = "#"+ clnumber.toString();
}
codepen - https://codepen.io/nagasai/pen/NLBXJE
Please refer this link for more details - https://developer.mozilla.org/en-US/docs/Web/API/Document/getElementsByTagName
I just change appendChild to document.body.appendChild(helloDiv) and added ID attribute for that div:
var helloDiv = document.createElement("div");
helloDiv.id = "myDIV";
document.body.appendChild(helloDiv);
var helloText = document.createTextNode("Click me");
helloDiv.appendChild(helloText);
var complementary = new Array();
var j = 0;
window.onclick = function(){
var background_color;
var body = document.getElementsByTagName("body")[0];
var helloText = document.getElementById("myDIV");
// var color = new Array();
var result = null;
var number = Math.round(Math.random()*0xFFFFFF);
for(var i = 0; i > 3; i++)
{
complementary[i] = (255-(number.slice(j,j+1).toString(10))).toString(16);
j = j + 2;
}
var clnumber = (complementary[6]+complementary[1]+complementary[2]).toString(16);
var clnumber2 = (complementary[0]+complementary[2]+complementary[6]).toString(11);
body.style.backgroundColor = "#"+ number.toString();
helloText.style.color = "#"+number.toString();
}

modify function for local HTML code

I have function that works perfect, but not for my scope:
function _svgToCanvas() {
var nodesToRecover = [];
var nodesToRemove = [];
var svgElems = document.getElementsByTagName('svg');
for (var i = 0; i < svgElems.length; i++) {
var node = svgElems[i];
var parentNode = node.parentNode;
var svg = parentNode.innerHTML;
var canvas = document.createElement('canvas');
canvg(canvas, svg);
nodesToRecover.push({
parent: parentNode,
child: node
});
parentNode.removeChild(node);
nodesToRemove.push({
parent: parentNode,
child: canvas
});
parentNode.appendChild(canvas);
}
}
I'm trying to modify it for using local code that comes from param, like this:
function _svgToCanvas(content) {
var nodesToRecover = [];
var nodesToRemove = [];
var svgElems = content.getElementsByTagName('svg');
for (var i = 0; i < svgElems.length; i++) {
}
return content;
}
var content = $('#main_contents').get(0);
result = _svgToCanvas(content);
But I can't modify the for loop. How to modify it?
Looks like the "var svg = parentNode.innerHTML;" doesn't give you the correct parameter for function canvg.
This piece of code comes from canvg.js, try it.
function _svgToCanvas(content) {
var svgTags = content.querySelectorAll('svg');
for (var i=0; i<svgTags.length; i++) {
var svgTag = svgTags[i];
var c = document.createElement('canvas');
c.width = svgTag.clientWidth;
c.height = svgTag.clientHeight;
svgTag.parentNode.insertBefore(c, svgTag);
svgTag.parentNode.removeChild(svgTag);
var div = document.createElement('div');
div.appendChild(svgTag);
canvg(c, div.innerHTML);
}
return content;
}
This funtion will not change the original content, and just return a new dom node.
function _svgToCanvas(content) {
var newContent = content.cloneNode(true);
var svgTags = newContent.querySelectorAll('svg');
var svgTagsOriginal = content.querySelectorAll('svg');
for (var i=0; i<svgTags.length; i++) {
var svgTag = svgTags[i];
var svgTagOriginal = svgTagsOriginal[i];
var c = document.createElement('canvas');
c.width = svgTagOriginal.clientWidth;
c.height = svgTagOriginal.clientHeight;
svgTag.parentNode.insertBefore(c, svgTag);
svgTag.parentNode.removeChild(svgTag);
content.appendChild(c);
var div = document.createElement('div');
div.appendChild(svgTag);
canvg(c, div.innerHTML);
}
return newContent;
}

Javascript array to point variable name with similar function

I'm want to shorten this function with array
document.mySchedule.breakfast.onchange = function() {
var id = document.mySchedule.breakfast.selectedIndex;
var val = document.mySchedule.breakfast[id].value;
strUser[0]=val;
}
document.mySchedule.lunch.onchange = function() {
var id = document.mySchedule.lunch.selectedIndex;
var val = document.mySchedule.lunch[id].value;
strUser[1]=val;
}
document.mySchedule.dinner.onchange = function() {
var id = document.mySchedule.dinner.selectedIndex;
var val = document.mySchedule.dinner[id].value;
strUser[2]=val;
}
I'm try this way but it didn't seem to be work.
var selectData = ["breakfast","lunch","dinner"]
for(i = 0; i < selectData.lenght; i++) {
document.mySchedule.selectData[i].onchange = function() {
var id = document.mySchedule.selectData[i].selectedIndex;
var val = document.mySchedule.selectData[i][id].value;
strUser[i]=val;
}
}
by the way this use to control selector.
Hope someone can help. thank you
Use:
var selectData = ["breakfast","lunch","dinner"]
for(i = 0; i < selectData.lenght; i++) {
var e = document.getElementById(selectData[i]);
e.onchange = function(){
strUser[i] = e.value;
};
}

Create variables with a For each loop - jquery

I have the following
var invest401_2 = $("input[type=hidden][name=invest401_2]").val();
var invest401_3 = $("input[type=hidden][name=invest401_3]").val();
var invest401_4 = $("input[type=hidden][name=invest401_4]").val();
var invest401_5 = $("input[type=hidden][name=invest401_5]").val();
var invest401_0label = Math.round(((invest401_0/balance401)* percent401kb));
var invest401_1label = Math.round(((invest401_1/balance401)* percent401kb));
var invest401_2label = Math.round(((invest401_2/balance401)* percent401kb));
var invest401_3label = Math.round(((invest401_3/balance401)* percent401kb));
var invest401_4label = Math.round(((invest401_4/balance401)* percent401kb));
var invest401_5label = Math.round(((invest401_5/balance401)* percent401kb));
$("#invest401_0").text(invest401_0label+'%');
$("#invest401_1").text(invest401_1label+'%');
$("#invest401_2").text(invest401_2label+'%');
$("#invest401_3").text(invest401_3label+'%');
$("#invest401_4").text(invest401_4label+'%');
$("#invest401_5").text(invest401_5label+'%');
Having the count total - ex. 5
How do a throw this into a for each loop.
I tried but didnt work.
Try this
var invest401_label = [];
var invest401 = [];
for(i=0;i<6;i++)
{
invest401[i] = var invest401_2 = $("input[type=hidden][name=invest401_"+i+"]").val();
invest401_label[i] = Math.round(((invest401[i]/balance401)* percent401kb));
$("#invest401_"+i).text(invest401_label[i]+'%');
}
Take a look at $.each.
http://api.jquery.com/jQuery.each/
If you add a class to this elements $("input[type=hidden][name=invest401_2]").val(); you can get them as an array and use each.
If you add a class named elements. Use the following example.
$('.elements').each(function(i, element) {
var invest = $(element).val();
$(element).val(Math.round((invest/balance401)* percent401kb));
});
Or
var $elements = $('.elements');
for(var i in $elements) {
var element = $elements[i];
element.val(Math.round((element.val()/balance401)* percent401kb));
}
Assuming there is only #invest401_0 - 5
$("[id=^invest401_]").each(function(){
$(this).text(Math.round((($("input[type=hidden][name="+this.id+"]").val()/balance401)* percent401kb))+'%');
});
Reference
http://api.jquery.com/jQuery.each/
http://api.jquery.com/category/selectors/
Although this may not work ( I'm currently writing this from an ie8 machine) this /should/ do what you want correctly and replaces all of the code you have there
for (i = 0; i < $('.hiddenelems').size(); i++) {
$('.hiddenelems:eq('+i+')').text(Math.round((($('.hiddenelems:eq('+i+')').val()/balance401)* percent401kb))+'%');
}

Categories