Remove DIV using button - javascript

Let's say I have a div with a button inside:
<div>
<button id='delete_btn'>delete</button>
</div>
What would be the jQuery code to delete that div and ONLY that div
As I have another button that dynamically adds copies of that sample code above.
So I could have something like this, but I only want the div that contains the button pressed, to be deleted.
<div>
<button id='delete_btn'>delete</button>
</div>
<div>
<button id='delete_btn'>delete</button>
</div>
thanks!

id should not be duplicate in a document. Use class instead. Inside the click handler function, you can target the parent of this element to remove:
$(document).on('click', '.delete_btn', function(){
$(this).parent().remove();
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div>
<button class='delete_btn'>delete</button>
</div>
<div>
<button class='delete_btn'>delete</button>
</div>

This can easily be performed with Vanilla JS and the newer remove() method. If IE-support is not a necessity, consider the following; or, if IE-support is needed, it wouldn't take much to amend the following:
document.addEventListener('click', function (e) {
if (e.target.matches('.delete_btn'))
e.target.parentNode.remove()
}, false);
<div>
<button class='delete_btn'>delete 1</button>
</div>
<div>
<button class='delete_btn'>delete 2</button>
</div>
event / state
This binds an event to the document (ancestor of the button). The benefit from this is that the click handler will be called for any new delete buttons that are dynamically created after the page has loaded (and will still function).
class vs id
This also uses class in place of id. This is because id should be reserved for unique values and class is intended to be a handle to like-elements. JavaScript can produce unexpected behavior if multiple elements are named with the same ID.
remove()
Using remove() an element can be removed from the DOM as expected. An older method would be to call the removeChild() on the parent (e.g., parent=e.target.parentNode; parent.parentNode.removeChild(parent))
more ES6
Of course, you could simplify the code using a named-argument/destructuring-assignment, which essentially assigns event.target to a variables named btn and The code can further be reduced, using a common arrow function. See below.
document.addEventListener('click', ({target: btn})=>{
btn.matches('.delete_btn') && btn.parentNode.remove()
}, false);
<div><button class='delete_btn'>delete 1</button></div>
<div><button class='delete_btn'>delete 2</button></div>
{target: btn} plucks the event argument being passed into the function and takes the value of the target property and assigns it to a new variable called btn. If you just had {target} (without the assignment), in the function body you would replace btn with target (e.g., target.matches(…), target.parentNode)

Related

How to add event listeners using a for loop to dynamically generated buttons

I have a page w/ dynamically generated buttons and i'm trying to add event listeneners to them using a for loop.
I'm not sure why my code is not working as it refers the each button via it's ID and uses dot notation to add the event listener. There is some commenting in the code to help clarify.
Here is abbreviated markup showing the buttons only
<button class="btnRollDice" id="btnRollDiceP1">Roll Dice!</button>
<button class="btnRollDice" id="btnRollDiceP2">Roll Dice!</button>
<button class="btnRollDice" id="btnRollDiceP3">Roll Dice!</button>
Here is the js
rollDiceBtns = document.getElementsByClassName('btnRollDice');//returns a HTML collection
function addEventListeners(){
console.log(rollDiceBtns);
for(i=0;i<rollDiceBtns.length;i++){
console.log(rollDiceBtns[i].id); //THIS WORKS,
rollDiceBtns[i].id.addEventListener('click', rollDice, false); //THIS DOES NOT
}
}
How would this be done using a for loop? to dynamically generated buttons?
addEventListener is a method you find on elements.
rollDiceBtns[i] is an element.
rollDiceBtns[i].id is a string.
Remove .id.

A deleting button deletes itself instead of the targeted element

I got a really bothering problem which I can not understand.
I have a div which contains 2 paragraphs, and a clickable button to delete the first p element, but the strange thing is that the button deletes it self and the p element continues to live!
This is the result of my code:
But when I click on the button I get this:
Below is my code:
<div>
<p id="id_1">The first paragraph.</p>
<p id="id_2">The second one.</p>
</div><br>
<button onclick="remove(document.getElementById('id_1'));">click me!</button>
<script>
function remove(elem)
{
var parent=elem.parentNode;
parent.removeChild(elem);
}
</script>
The function name "remove" is being hidden by the native "remove" method on the button element itself. If you change the name, it works as expected.
Event handlers established with HTML "onfoo" attributes execute in a specially-constructed scope that includes the methods (and other properties) on the DOM node for the element. That's just one of many reasons that it's preferable to use JavaScript to attach event handlers via addEventListener().
All you need to do is to rename your function and avoid using remove as its name(The reason for this is included in #Pointy's answer). Try this:
<div>
<p id="id_1">The first paragraph.</p>
<p id="id_2">The second one.</p>
</div><br>
<button onclick="removeElement(document.getElementById('id_1'));">click me! </button>
<script>
function removeElement(elem)
{
var parent=elem.parentNode;
parent.removeChild(elem);
}
</script>

When a Div class is clicked, alert it's inner content's Div Class

How do i even put these, let me try. In the following sets of codes, i want to click 'parentclass' and have an alert value of 'child1' and when i click the class below it which is 'Parent 2' have an alert fire with a value of 'child2'
So this must alert the content of that class only and not the entire class.
Here's some Javascript in Jquery.
var childclass = $('.childclass').html();
$('.parentclass').click(function(e) {
alert (childclass)
});
$('.childclass').click(function(e) {
e.stopPropagation()
e.preventDefault()
});
And HTML
<a href="" onClick="return false">
<div class='parentclass'>
Parent 1
<div style="display:none" class="childclass">child1</div>
</div>
</a>
<a href="" onClick="return false">
<div class='parentclass'>
Parent 2
<div style="display:none" class="childclass">child2</div>
</div>
</a>
This line var childclass = $('.childclass').html(); doesnt make sense as it doesn't know which element in particular you mean. The result of that will just be child1child2 which is just a concatenation of the .html() of all the elements with class childclass. This is obviously not what you want.
Therefore you should dynamically find the child with a class of childclass upon receiving the click event.
$('.parentclass').click(function(e) {
alert($(this).find('.childclass').html())
});
Also, you should know that your child class event handler is useless as we don't care if the event gets propogated downwards. If you DID care, then your e.stopPropagation() and e.preventDefault() should be in the event handler of the parent class.
You need to fetch the html of the clicked parent element within the click handler
$('.parentclass').click(function (e) {
alert($(this).find('.childclass').html())
});
$('.childclass').click(function (e) {
e.stopPropagation()
e.preventDefault()
});
Demo: Fiddle
Several ways you can go about this.
First, if your HTML will not be dynamic (elements already exist when page loads), then you can select elements by the parent class name and assign click event as so:
$('.parentclass').click(function(e) {
// the first variable here is selecting the inner elements having class 'childclass'
// keep in mind, if more than one child having that class is present within this parent, it will select all of them
var child = $(this).find('.childclass');
// here we alert the text of the inner child found
// if it is more than one, you will have undesired results. you may want to specify `.first()`
alert(child.text())
})
For newer jQuery you can also use $('.parentclass').on('click', function(e) {.
If you expect any pieces of parentclass to be dynamic, then you'll want to delegate the event based on either a static parent to the parents or document. This can be like so:
$(document).on('click', '.parentclass', function(e) {
alert($(this).find('.childclass').text())
})
Or, if you have a static (already there when page loads) wrapping element, give it an ID like `parentClassWrapper' and assign the click event dynamically as:
$('#parentClassWrapper').on('click', '.parentclass', function(e) {
alert($(this).find('.childclass').text())
})
Some helpful links:
jQuery API
jQuery Selectors
.click()
.on()
Some info on Event Delegation
jquery on vs click methods
jQuery .on('click') vs. .click() and .delegate('click')
jquery .live('click') vs .click()
I made several adjustments to your html that are worth noting. There's no need for the <a> tag. Don't use inline js - onlick in your html. Note that I wrapped the text inside of the div in the <a> tag instead. This markup is more semantic. Also, move your styles to css rather than in the html.
<div class="parent">
<a>Parent 1</a>
<a class="child">child of parent 1 contents</a>
</div>
<div class="parent">
<a>Parent 2</a>
<a class="child">child of parent 2 contents</a>
</div>
css:
.parent > .child { /* good practice: only select an immediate child of the parent */
display: none;
}
The other answers here are using find() to select the child, but I recommend children() instead. For example, if you had additional nested .childs, find() will select them all, but children() will only select direct .childs of the parent, so it is better in this case. I also recommend using the console for debugging rather than alert.
Live demo here (click).
$('.parent').click(function() {
var $child = $(this).children('.child');
var cls = $child.attr('class');
console.log(cls);
$child.show(); //added so that you can click the child
});
$('.child').click(function() {
var html = $(this).html();
console.log(html);
//if you just want the text, use this instead:
var text = $(this).text();
console.log(text);
});

I need to pass two elements to an onclick event handling function JavaScript and not just their id's

Suppose I have two elements in my code and I want to pass their respective id's to an event handling function. (In my example below, I have a div and a button)
<div id="div1">
<input type="button" id="button1" onclick="doSomething(this, [here comes id of div])" />
</div>
For the button, instead of writing the id which is "button1", I simply passed the element itself using the this keyword. Now my question is, is there a way where I can pass the div element itself in the function and not just its id just like what I did with the button element?
Any help would be greatly appreciated.
You can use the parentNode property;
this.parentNode
As this returns a DOMElement (similar to this), you can access the ID the same via;
this.parentNode.id
... should you want to.
Just get it from the parent in the callback:
function clickHandler(e){
console.log(e.target.parentNode.id);
}
Why do you need to pass it in the first place? Access the div via parentNode.
onclick="doSomething(this);"
and
function doSomething(btn) {
var div = btn.parentNode;
}

Jquery Click to hide/show div not working

Need to use one single button to toggle the show and hide for div
my code looks something like this
function showTable(number){
$('#div_'+number).show('slow');
$('#button_'+number).html("Hide Table").click(function(){
hideTable(number);
return false;
});
}
function hideTable(number){
$('#div_'+number).hide('slow');
$('#button_'+number).html("Show Table").click(function(){
showTable(number);
return false;
});
}
<div id="div_1" style="display:none"></div>
<button id="button_1" onClick="javascript:showTable(1)">Show Table</button>
<div id="div_2" style="display:none"></div>
<button id="button_2" onClick="javascript:showTable(2)">Show Table</button>
<div id="div_1" style="display:none"></div>
<button id="button_3" onClick="javascript:showTable(3)">Show Table</button>
The function is working fine at first. But after i show and hide it once, whenever I tried to show it again, it starts chaining show/hide/show/hide by itself without any clicks. And the more I do it, the longer it does the chaining. It seems it's just a loop that everytime it doubles the amount of looping(like show/hide for 2/4/8/16/32 times ....) the more I do the longer it loops. Anyone have a clue what's going on?
I tried to remove the click part in the hideTable function, the loop stops but still whenever I try to hit showTable, it will show then hide it self automatically like it's auto executing the stuff in the click function without any clicks...
Also is there anyway to use the jquery tagging style to call the function instead of using onclick? i know I can do like
$("#button_1").click(function(){......................});
$("#button_2").click(function(){......................});
$("#button_3").click(function(){......................});
but is there anyway I can group all of them together into a single function and still able to tell which button is clicked? Because I need a way to track which div to show and hide, and change the the text in corresponding button. Thank you very much in advance. m(_ _)m
You're piling on more and more redundant event handlers with each "click". That's what those calls to ".click()" in the handlers do — add another event handler.
You only need to add an event handler once. And adding an event handler does not remove the prior handler. Since you're using jQuery, use it to add the handlers, not old-fashioned "onclick" attributes.
Give all those <div> elements a class value, like "toggled".
<div id="div_1" style="display:none" class='toggled'>
You can do the same with the buttons. Then you can set up event handlers by using the class to refer to them in a jQuery selector.
A better way to do this is with toggle. Refer to JQuery toggle showhide
you should gove all your divs the same class eg class="toggleable" on the ones you want to toggle.
Then try:
jQuery(".toggleable input[type='button']").click(function()
{
jQuery(this).closest("div.toggleable").toggle();
});
This will put an onlick on your buttons inside your div which will find the closest parent div with class toggleable and will either hide/show your div.
To read about toggle():
http://api.jquery.com/toggle/
to read about selectors:
http://api.jquery.com/category/selectors/
I agree with Pointy but since I can't seem to add onto the answer, I must make another.
$('[data-show-table]').click(function() {
var $this_button = $(this);
$('#div_' + $(this).attr('data-show-table')).toggle(function() {
var msg = $(this).css('display') == 'none' ? 'Show table' : 'Hide table';
$this_button.html(msg);
});
});
<div id="div_1" style="display:none">Table 1</div>
<button id="button_1" data-show-table="1">Show Table</button>
<div id="div_2" style="display:none">Table 2</div>
<button id="button_2" data-show-table="2">Show Table</button>
<div id="div_3" style="display:none">Table 3</div>
<button id="button_3" data-show-table="3">Show Table</button>

Categories