Issue with creating clones of HTML div using JQuery - javascript

I am trying to create clones of a HTML div. The div has a label and two text boxes inside it. I need to change the label value of the newly created div. Here is my code.
<body>
<div id="PayDiv2">
<label id="PayLbl2">Payment No 2: </label>
<input type="text" />
<input type="text" />
</div>
<div id ="totPayForm" >
<label id="totPayLbl">Total Payment: </label>
<input type="text" />
<input type="text" />
<input type="submit" value="Add new one" onclick="addNewField();
return false;">
</div>
<input type="button" value="Clone box" id="btn" />
<script src="//ajax.googleapis.com/ajax/libs/jquery/1.10.2/jquery.min.js"></script>
<script>
var i=3;
//When DOM loaded we attach click event to button
$(document).ready(function() {
$('#btn').click(function() {
var cloned = $('#PayDiv2').clone();
cloned.insertBefore("#totPayForm");
$('#PayLbl2').html("Payment No "+ i++ + ':');
});
});
</script>
</body>
The problem is the place the newly created clones placed. First clone get placed before everything(even though I need to place it after the original div which I used to create divs. )
divs generated after that also get placed at first and, early divs goes down. It is hard to describe here. If you can be kind enough to run my code you will see what the issue is.
I have an another requirement to generate unique ids to cloned divs. Since I am new in JQuery, I found it difficult to generate id's.
I am pleased if you can help me in this case. Thank you all.

The problem is $('#PayLbl2').html("Payment No "+ i++ + ':'); it always changes the first element's label instead of the clone(because of the duplicated ids)...
so use class instead of id
<div class="PayDiv2">
<label class="PayLbl2">Payment No 2:</label>
<input type="text" />
<input type="text" />
</div>
then
var i = 3;
//When DOM loaded we attach click event to button
$(document).ready(function () {
$('#btn').click(function () {
var cloned = $('.PayDiv2').first().clone();
cloned.insertBefore("#totPayForm");
cloned.find('.PayLbl2').html("Payment No " + i+++':');
});
});
Demo: Fiddle

Here it is.
Demo
Make your HTML like below
<div id="PayDiv0" class="PayDiv0">
<label id="PayLbl0" class="PayLbl2">Payment No 2:</label>
<input type="text" />
<input type="text" />
</div>
<div id="totPayForm">
<label id="totPayLbl">Total Payment:</label>
<input type="text" />
<input type="text" />
<input type="submit" value="Add new one" onclick="addNewField();
return false;">
</div>
<input type="button" value="Clone box" id="btn" />
And JS should be like this
var i = 3;
$(document).ready(function () {
$('#btn').click(function () {
var cloned = $('.PayDiv0').first().clone();
var noOfDivs = $('.PayDiv0').length;
cloned.insertBefore("#totPayForm");
cloned.attr('id', 'PayDiv' + noOfDivs);
cloned.find('label').attr('id', 'PayLbl' + noOfDivs);
cloned.find('.PayLbl2').html("Payment No " + i+++':');
});
});

As mentioned in the answer by #Arun P Johny, set the div id PayDiv0
$('#btn').click(function () {
var cloned = $('.PayDiv2').first().clone();
// find total divs with class PayDiv2
var noOfDivs = $('.PayDiv2').length;
cloned.insertBefore("#totPayForm");
// add new id to the cloned div
cloned.attr('id', 'PayDiv' + noOfDivs);
// find the label element inside new div and add the new id to it
cloned.find('label').attr('id', 'PayLbl' + noOfDivs);
cloned.find('.PayLbl2').html("Payment No " + i+++':');
});
this way you can add the dynamic ids to your elements.

Related

Add one div at a time, or delete duplicates fields

I have a part of a project I'm working on in which I have to add repeated instances of the same div. It mostly works, however, instead of adding individual instances, the previous div added seems to be repeating itself, rather than having the "original div" adding.
Here is the jsfiddle together with the code I'm using so far:
<div class="shape" id="plan4_shape">
<span class="bakkant">
<input class="measures" id="plan4_width" placeholder="mm" name="p4width" value="w1"/>
<span class="times"> ×</span>
<input class="measures" id="plan4_width" placeholder="mm" name="p4length" value="l1" />
</span>
<script id="template" type="text/template">
<span class="bakkant" id="bakkant">
<input class="measures" id="plan4_width" placeholder="mm" name="p4width" value="w"/>
<span class="times"> ×</span>
<input class="measures" id="plan4_width" placeholder="mm" name="p4length" value="l" />
<button class="close" id="close">×</button>
</span>
</script>
<button type="button" name="add_row" class="addrow" id="addrow4" onClick="addrow()">Add row</button>
<textarea name="more_info" id="profiles" placeholder="Beskriv fritt, vilka kanter du vill få profilerade."></textarea>
</div>
jQuery code
$(function() {
var i = 0;
$('#addrow4').click(function() {
var $clone = $($('#template').html());
$clone.attr('id', "bakkant" + ++i);
$clone.find('p').attr("Bob" + ++i)
$clone.find('input').attr('value', "l" + ++i);
$clone.find('input').attr('value', "w" + ++i);
$('.bakkant').append($clone);
});
$('.shape').on('click', '.close', function() {
$(this).closest('.bakkant').remove();
});
});
As you need to add the new row at the last, you need to do
$('.bakkant').last().append($clone);
You need not do ++i for changing every id or value attribute, just increment it once for each event.
Working Fiddle here.

How do I repeat the piece of html code 10 times by clicking on the same button using JS/Jquery?

I want to be able to display the same piece of html code 10 times under the div called: <div id="add_remove_product_name"> By clicking on the button called: <button id="add_another_product_name">. I think I need some kind of a for loop for the job but are not sure. Any suggestion will be helpful, thanks.
My HTML code:
<div id="product_name">
<input id="skriv_produktnavn" placeholder="Skriv Produktnavn her" required></label>
<button id="add_another_product_name">Tilføj endnu et produktnavn</button>
<div id="add_remove_product_name">
<input id="added_product_name" placeholder="Skriv Produktnavn her" required></label>
<button id="remove_product_name">X</button>
</div>
Use a for loop to concatenate 10 copies of the HTML code. Then use .after() to put this after the DIV.
$("#add_another_product_name").click(function() {
var html = '';
for (var i = 0; i < 10; i++) {
html += 'html code that you want to repeat';
}
$("#add_remove_product_name").after(html);
}
You can use jQuery clone() however when cloning an element all the attributes will be the same. Fo example they will all have the same id attribute which will cause problems and it is not valid html
So in order to do the clone correctly you have fix the cloned element
DEMO: http://jsfiddle.net/rpyt445e/
var $tpl = $('#product_name').clone();
var num = 0
$('#clone').click(function () {
num++;
var $cloned = $tpl.clone();
$cloned.attr('id', $tpl.attr('id') + '_' + num);
$(':not([id=""])', $cloned).each(function(){
$(this).attr('id', $(this).attr('id') + '_'+num);
});
$cloned.appendTo('#wrapper');
});
HTML:
<div id="wrapper">
<div id="product_name">
<input id="skriv_produktnavn" placeholder="Skriv Produktnavn her" required />
<button id="add_another_product_name">Tilføj endnu et produktnavn</button>
<div id="add_remove_product_name">
<input id="added_product_name" placeholder="Skriv Produktnavn her" required />
<button id="remove_product_name">X</button>
</div>
</div>
</div>
<button id="clone">Clone</button>
A technique for adding the additional elements without having to create ugly strings of html in the JavaScript is to start with one hidden set of the elements in the html. At page load time, you remove that set, but keep a reference to it. Then when you want to add a set to the page, you clone the set you removed. All of this is easier if you add a container div around the additional inputs.
You also need to make sure id attribute values are unique. In the case of the remove buttons, you can replace the id with a class. As for the input id values, if you really need them, you can add an index value to them.
Since the remove buttons are dynamically added, I suggest using event delegation when binding the click-handler.
HTML:
<div id="product_name">
<input id="skriv_produktnavn" placeholder="Skriv Produktnavn her" required="required"/>
<button id="add_another_product_name">Tilføj endnu et produktnavn</button>
<div id="additional_product_names">
<div class="add_remove_product_name" style="display: none;">
<input id="added_product_name" placeholder="Skriv Produktnavn her" required="required"/>
<button class="remove_product_name">X</button>
</div>
</div>
</div>
JavaScript:
$(function() {
var MAX = 10;
var $addBtn = $('#add_another_product_name'),
$additionalContainer = $('#additional_product_names');
$TEMPLATE = $additionalContainer.children(':first').remove();
function update() {
var $additonalDivs = $additionalContainer.children();
// Enable/disable the add button.
$addBtn.prop('disabled', $additonalDivs.length >= MAX);
// Re-index the "id" attributes.
$additonalDivs.find('input').attr('id', function(i) {
return 'added_product_name[' + i + ']';
});
}
$addBtn.click(function() {
$TEMPLATE.clone().appendTo($additionalContainer).show();
update();
});
$('#product_name').on('click', '.remove_product_name', function() {
$(this).closest('.add_remove_product_name').remove();
update();
});
});
jsfiddle

Increment of counter on dynamic addition of rows

I'm trying to add the rows dynamically plus auto-increment of a counter.I want to start with 1 then 2 then 3 and so on . I have added my code on plunker ,in which every time the max value is getting in first column like 4 then 1,1,2,3.Where am i going wrong ?i Want it to be 1,2,3,4.
Here is the plunker link http://plnkr.co/edit/GuDbJ3SHOPvWkHfNfd8E?p=preview
var _counter = 0;
function Add() {
_counter++;
var oClone = document.getElementById("template").cloneNode(true);
oClone.id += (_counter + "");
document.getElementById("placeholder1").appendChild(oClone);
document.getElementById("myVal").value=_counter;
}
<div id="placeholder1">
<div id="template">
<div>
Value:<input type="text" id="myVal" placeholder="1">
Quantity:<input type="text" placeholder="Qty">
<input type="button" onClick="Add()" value="Click! ">
</div>
</div>
I think it is because you have multiple divs with the id="myVal". The id attribute should be unique on the page. If not, your page will still load, but you may have unexpected behavior.
You are changing the id of the template div, but not the myVal div.
I assume you are looking for something like this:
var _counter = 0;
function Add() {
_counter++;
var oClone = document.getElementById("template").cloneNode(true);
oClone.id += (_counter + "");
document.getElementById("placeholder1").appendChild(oClone);
oClone.getElementsByClassName("myVal")[0].value = _counter;
}
<div id="placeholder1">
<div id="template">
<div>
Value:
<input type="text" class="myVal" placeholder="1">Quantity:
<input type="text" placeholder="Qty">
<input type="button" onClick="Add()" value="Click! ">
</div>
</div>
</div>
In your original you are cloning your template with the same id for the input. So when you do document.getElementById("myVal").value=_counter;, you only get the first input. I changed it to use class instead and get the input with the appropriate class that is a child of the cloned node.

adding dynamic content using javascript DOM

I want the following functionality in my webpage :-
when the add button is clicked, an entire div should get appended to a span. To achieve this I have attempted the below, but it does not seem to be working. Please explain why and how can i get this done.
<html>
<head>
<script type="text/javascript">
function add()
{
var details=document.getElementById('education');
var eachDetail=document.getElementById('fdetails_edu_div');
alert(details.getAttribute('id'));
alert(eachDetail.getAttribute('id'));
var x=details.appendChild(eachDetail);
alert(x);
}
</script>
</head>
<body>
<span id="education">
<div id="fdetails_edu_div">
<label>EDUCATIONAL QUALIFICATION
<span class="small">Click on 'ADD' to add more qualifiaction details</span>
</label>
<button type="button" name="addqualifiaction" onclick="add()">ADD</button>
<br>
<br>
<br>
<label>Degree
<span class="small">School/Board</span>
</label>
<p>
<input type="text" name="school_board" id="fdegree" size="30" maxlength="30" value="none" class="fprjtit"/>
</p>
<br>
<br>
<br>
<label>Year
<span class="small">Year of Passing</span>
</label>
<p>
<input type="text" name="pass_year" id="fdegree" size="30" maxlength="30" value="none" class="fprjtit"/>
</p>
<br>
<br>
<br>
<label>Max Marks
<span class="small">maximum marks</span>
</label>
<p>
<input type="text" name="max_marks" id="fdegree" size="30" maxlength="30" value="none" class="fprjtit"/>
</p>
</div>
</span>
</body>
</html>
now when i click on the add button the div with the id "fdetails_edu_div" should get appended as a child, preferably to the bottom, of the span with the id "education".
What is wrong with the below and how can it be corrected?
I think you need to clone the div with id fdetails_edu_div
Use the following code
var x = 1;
function add() {
var container = document.getElementById('education');
var detail = document.getElementById('fdetails_edu_div');
var clone = detail.cloneNode(true);
clone.id = "fdetails_edu_div" + x;
x++;
container.appendChild(clone);
}
Notice, I create a new id for the newly created div.
Also note, I have removed the Add button from within the div fdetails_edu_div and placed it outside (you don't want the add button to repeat, do you?)
See working fiddle
The usage of appendChild() is move an element from one element to another,check this.
Based on your code, you move the 'eachDetail' to 'details', but 'eachDetail' is already there. It works like you remove the 'eachDetail' and then add it again in the 'details', so nothing happens.
You can replace 'details' with another element, a new span.
Try this code
function add()
{
var arr = [];
var n = 0;
var details=document.getElementById('education');
var eachDetail=document.getElementById('fdetails_edu_div');
alert(details.getAttribute('id'));
alert(eachDetail.getAttribute('id'));
node = document.getElementById("fdetails_edu_div");
while (node.firstChild) {
arr[n++] = node.firstChild;
node.removeChild(node.firstChild);
}
for(var i = 0; i < n; ++i) {
details.appendChild(arr[i]);
}
alert(eachDetail.parentNode.getAttribute('id'));
}
Above code first removes the child nodes of div with id fdetails_edu_div, saves them temporarily and later appends them to span with id education. You can check this with alert(eachDetail.parentNode.getAttribute('id'));

Adding and removing dom sections with javascript

I want to be able to add new sections (via the 'add' link) and remove them (via the 'x' button) like seen in the image.
The HTML for the image:
<fieldset>
<legend>Legend</legend>
<div id="section0">
<input type="text" name="text1" value="Text1" />
<input type="text" name="text2" value="Text2" size='40' />
<input type="button" value="x" style="width: 26px" /><br />
</div>
add<br />
</fieldset>
I guess I could add new sections as needed (i.e. section1, section2) and delete those sections according to which button was pressed. There would be a javascript function that would inject sections in the DOM everytime the 'add' link was clicked and another for deleting a section everytime the 'x' button was clicked.
Since I have so little experience in HTML and Javascript I have no idea if this is a good/bad solution. So, my question is exactly that: Is this the right way to do it or is there a simpler/better one? Thanks.
P.S.: Feel free to answer with some sample code
Here's one way to do it:
<script type="text/javascript">
function newrow() {
document.getElementById("customTable").innerHTML += "<tr><td><input type='text'></td><td><input type='text'></td><td><button onclick='del(this)'>X</button></td></tr>";
}
function del(field) {
field.parentNode.parentNode.outerHTML = "";
}
</script>
<body onload="newrow()">
<fieldset>
<legend>Legend</legend>
<table>
<tbody id="customTable">
</tbody>
</table>
<button onclick="newrow()">Add</button>
</fieldset>
</body>
You could add IDs to them if you wanted, or you could call them by their position document.getElementsByTagName("input")[x].value The inputs would start at 0, so the left one is 0, right is 1, add row: left is 2, right is 3, etc.
If you delete one, the sequence isn't messed up (it re-evaluates each time), which is better than hard-coded IDs.
I just answered a nearly identical question only a few minutes ago here using jQuery: https://stackoverflow.com/a/10038635/816620 if you want to see how it worked there.
If you want plain javascript, that can be done like this.
HTML:
<div id="section0">
<input type="text" name="text1" value="Text1" />
<input type="text" name="text2" value="Text2" size='40' />
<input type="button" value="x" style="width: 26px" /><br />
</div>
add<br />
Javascript:
function addSection(where) {
var main = document.getElementById("section0");
var cntr = (main.datacntr || 0) + 1;
main.datacntr = cntr;
var clone = main.cloneNode(true);
clone.id = "section" + cntr;
where.parentNode.insertBefore(clone, where);
}​
Working demo: http://jsfiddle.net/jfriend00/TaNFz/
http://pastebin.com/QBMEJ2pq is a slightly longer but robust answer.

Categories

Resources