Show/Hide Div element with javascript button click - javascript

I have a site using Google Maps Api which adds and saves markers. When a saved marker is clicked, it displays an info window which has a Button in it. When this button is clicked, I want it to display a hidden DIV element which contains a Table of the saved marker details.
The JS which contains the InfoWindow is:
var eventContent = $('<div class="event-info">' + '<h4 class="event-name">' + point.name + '</h4><hr>' +
'<span><h5>Date: </h5>' +
'<p class="event-date">' + point.edate + '</p></span>' +
'<p class="event-description">'+ point.description +'</p>' +
'<button id="remove-event" name="remove-event" onclick="showDetails();" class="remove-event btn btn-danger btn-sm" title="View Event">View Event</button>'+
'</div>');
// Display Event details on marker click
google.maps.event.addListener(event_markers[i], "click", function () {
infowindow.setContent(eventContent[0]);
infowindow.open(map, event_markers[i]);
map.setCenter(marker.getPosition());
map.setZoom(10);
});
The HTML DIV I want to display is:
<div class="event-details" id="event-details" style="display: none ">
<h3>Event Details</h3>
<table class="table">
<tr>
<th>Event Name: </th>
<td> Bill Gates</td>
</tr>
<tr>
<th>Event Date: </th>
<td> Bill Gates</td>
</tr>
</table>
<button type="button" class="btn btn-warning btn-sm"><span class="glyphicon glyphicon-remove"></span> Remove Event</button>
</div>
I have tried this, among other similar ideas but no luck.:
function showDetails()
{
if (document.getElementById("event-details").style.display == "none" ) {
document.getElementById("event-details").style.display="";
} else {
document.getElementById("event-details").style.display="none";
}

Your elements do not have an id of "event-details" but a class. Try using getElementsByClassName instead:
document.getElementsByClassName("event-details")[0].style.display = "none"// returns multiple elements so you should select the first (0th) item.
Maybe a better solution would be to add an "id" to your html element:
<div id="event-details" class="event-details" style="display: none ">
This way, your getElementById method should catch the elements you want.

Have you tried giving the div an ID?
maybe why the "getElementById" isn't working.
then:
document.getElementById("eventDetails").style.display="none";

FIXED.
My showDetails function had a syntax error, was missing a closing }
function showDetails()
{
if (document.getElementById("event-details").style.display == "none" ) {
document.getElementById("event-details").style.display="block";
}
else
{
document.getElementById("event-details").style.display="none";
}
}

Please use querySelector as below. Since you already have an id for the element you'd click on, like below:
<button id="remove-event" name="remove-event" class="remove-event btn btn-danger btn-sm" title="View Event">View Event</button>
You may remove the onclick inline event handler and do it the following way.
document.querySelector("#remove-event").addEventListener("click", function() {
var elem = document.querySelector("#event-details");
if (elem.style.display == "none") {
elem.style.display = "block";
} else {
elem.style.display = "none";
}
});

May be try these-
1) Change the div id to other instead of having the class name
2) Here you are checking for 'none', but i think if you are not showing the div anywhere in your code prior calling this code, you can remove the if clause, since that div was already hidden and if clause wouldn't work if its already hidden.
if (document.getElementById("event-details").style.display == "none" ) {
document.getElementById("event-details").style.display="";
}
3) Try to use- instead of
document.getElementById("event-details").style.display="";
to
document.getElementById("event-details").style.display=block;
or
document.getElementById("event-details").show();

Related

How to access a dynamically inserted table row

My page has a table with two rows, like this:
<table class="table table-condensed">
<tbody>
<tr>
<td class="col-sm-8 room-status" data-roomstatusid="1" data-value="Active" data-edited="false">Active</td>
<td class="col-sm-4"><i class="fas fa-pencil-alt edit-status" style="font-size: 20px;"></i>
<div class="edit-controls hidden"><i class="fas fa-times-circle cancel-status-edit" style="margin-left: 5px;font-size: 20px;"></i><i class="fas fa-save save-status-edit" style="margin-left: 15px;font-size: 20px;"></i>
</div>
</td>
</tr>
<tr id="status-template" class="hidden">
<td class="col-sm-8 room-status" data-roomstatusid="-1" contenteditable="true"></td>
<td class="col-sm-4"><i class="fas fa-pencil-alt edit-status hidden" style="font-size: 20px;"></i>
<div class="edit-controls" data-mode="new"><i class="fas fa-times-circle cancel-status-edit" style="margin-left: 5px;font-size: 20px;"></i><i class="fas fa-save save-status-edit" style="margin-left: 15px;font-size: 20px;"></i>
</div>
</td>
</tr>
</tbody>
</table>
There is a button on the page that adds a row at the start of the table using the html of the hidden #status-template row. All that works fine.
After the new row has been added, I can click the pencil icon on either it or what is now the second row (the one with "Active" in the first cell) and the javascript that detects the click works correctly.
If I click on the first <td> of the inserted row, the javascript that detects that click also works correctly, but if I click the first cell of what is now the second row (which contains "Active", the click is not detected.
My javascript is all delegated to the table element since I know there will be new elements added to the DOM.
The javascript to detect the click on the first <td> of a row looks like this
$('#room-status-table').on('click', 'tbody tr td:first', function() {
if ($(this).hasClass('row-highlight')) {
$(this).removeClass('row-highlight')
} else {
$('#room-status-table tbody tr').each(function() {
$(this)
.find('td:first')
.removeClass('row-highlight')
})
$(this).addClass('row-highlight')
}
})
The javascript to detect the click on the pencil icon is
$('#room-status-table').on('click', '.edit-status', function() {
var cell = $(this).closest('tr').find('.room-status')
$(cell).attr('contenteditable', 'true')
$(cell).focus()
$(this).addClass('hidden')
$(this).next().removeClass('hidden')
$(this).closest('tr').find('td:first').addClass('row-highlight')
})
The code that creates the new row is
$("#new-status").on("click", function() {
var html = "<tr>" + $("#status-template").html() + "</tr>"
$("table > tbody > tr:first").before(html)
$("table > tbody td:first").focus()
$("#edit-room-submit").attr("disabled", "disabled")
})
Grateful for any help in figuring out why the click on the first <td> of the second <tr> is not triggering my click event.
You've misunderstood the delegated selector td:first. What you will want to use is td:first-child.
While :first matches only a single element, the :first-child selector can match more than one i.e. one for each parent. This is equivalent to :nth-child(1).
Replace
.on('click', 'tbody tr td:first', ...)
with
.on('click', 'tbody tr td:first-child', ...)
I just did this at my project. I can share like an example my code which trigger one click and doubleClick at table row added via ajax:
$('table tbody').on('dblclick', 'tr', function(){
if(!$(this).hasClass('tr.selected-row')){
$(this).parent('tbody').find('tr.selected-row, td.selected-row').removeClass('selected-row');
$(this).addClass('selected-row').find('td').addClass('selected-row');
if($(this).find("td a[title='View']").length > 0){
var href = $(this).find("a[title='View']").attr("href");
if(href) {
window.location = href;
}
} else if($(this).find("td a[title='Update']").length > 0){
var href = $(this).find("a[title='Update']").attr("href");
if(href) {
window.location = href;
}
}
}
}).on('click', 'tr', function(){
if(!$(this).hasClass('tr.selected-row')){
$(this).parent('tbody').find('tr.selected-row, td.selected-row').removeClass('selected-row');
$(this).addClass('selected-row').find('td').addClass('selected-row');
}
})

My modal is not appearing, having difficulty targeting a button within a table using selectors

I am trying to have a "Delete confirm Modal" appear when clicking the delete button next to each row in a table. I'm not sure if its an issue with my JavaScript or the HTML.
$("#confirmDelete delete").on("click", function () {
$("#confirmDelete").modal('show');
});
$("delete").on("click", function () {
console.log("Ive been pushed");
var button = $(this);
$.ajax({
url: "/Services/DeleteService/" + button.attr("data-customer-id"),
method: "DELETE",
success: function () {
$(button.parent("tr")).remove();
console.log("Success");
}
});
});
<table id="services" class="table table-bordered table-hover">
#foreach (var service in Model)
{
<tr>
<td>#service.Name</td>
<td><button id="edit" class="btn btn-info edit">Edit</button> <button class="btn btn-danger delete" data-service-id=#service.Id data-target="#confirmDelete"><i class="fa fa-trash-o fa-lg"></i></button></td>
</tr>
}
</table>
Your jQuery selector on line 4 is looking for a delete tag instead of a delete class - its trying to find something like
<delete></delete>
If you want to add a click handler to the delete button, add a '.' before the selector to tell jQuery to find an element with the class 'delete', instead of the type of 'delete'. For example:
$(".delete").on("click", function () {
The '.' will look for elements with a class of delete.
P.S. your delete confirmation button will have the same problem, if you're looking for one with a class of 'delete'.

How to get the <tr> based on the data-* attribute of a child element?

I can get the id of the data already but the problem how to find that data on html
this is my html
<table cellspacing="0" cellpadding="0" border="0" id="cards" class="table table-striped table-bordered">
<thead>
<tr>
<th>Description</th>
<th>By</th>
<th>Total Votes</th>
<th></th>
</tr>
</thead>
<tbody>
<tr>
<td>If the opening scene of this show scared you as a kid, DRINK!</td>
<td>testing testing</td>
<td>1</td>
<td>
<a data-id="1" data-target="#viewCard" data-toggle="modal" class="btn btn-default btn-xs view" href="#"><span class="fa fa-eye"></span> View Card</a>
<a data-id="1" data-target="#editCard" data-toggle="modal" class="btn btn-primary btn-xs edit" href="#"><span class="fa fa-edit"></span> Edit</a>
<a data-id="1" data-target="#deleteCard" data-toggle="modal" class="btn btn-danger btn-xs delete" href="#"><span class="fa fa-remove"></span> Delete</a>
</td>
</tr>
...
</tbody>
</table>
so when the popup out... It will show button and this is the .submitDelete
Delete
and js
$(document).on('click', '.submitDelete', function(e){
e.preventDefault();
var card_id = $(".submitDelete").data('card_id');
var test = $("#cards table tr .delete[data-id='"+card_id+"']"); //<---- idk how to get the tr to be remove... this is what I've tried so far.
console.log(test);
});
EDIT1
I added jsfiddle so you guys know the flow
http://jsfiddle.net/sdxaV/1/
EDIT2
http://jsfiddle.net/sdxaV/12/
Based on the HTML you provided, the .submitDelete element does't have a card_id attribute.
Therefore, change $(".submitDelete").data('card_id') to $(this).attr('data-id') in order to retrieve the correct attribute of the clicked element, rather than the first matching element.
You were also trying to select a table element that is a descendant of a #cards element. The table element has an id of #cards, therefore the selector should be $("table#cards ..."). Or omit table from the selector.
Then to get the closest tr element, chain .closest('tr'):
Working Example
$(document).on('click', '.submitDelete', function(e) {
e.preventDefault();
var card_id = $(this).attr('data-card_id');
var $row = $("table#cards tr .delete[data-id='" + card_id + "']").closest('tr');
$row.remove();
});
I always use jQuery.closest() for this sort of thing. It will navigate up ancestors until it matches.
$(document).on('click', '.submitDelete', function(e){
e.preventDefault();
var test = $(this).closest('tr');
console.log(test);
});
In this circumstance, this is the .submitDelete button that was clicked.
With a Helper Library
The easiest way to do this is instead of making your own method to do this, pull in a library that already wraps the Bootstrap modal like Bootbox. Your example's delete link would be changed to the following:
<a data-id="1" class="btn btn-danger btn-xs delete" href="#"><span class="fa fa-remove"></span> Delete</a>
Your Javascript would be updated to the following:
$(document).on('click', '.delete', function(e){
e.preventDefault();
var $row = $(this).closest('tr');
bootbox.confirm("Are you sure?", function(result) {
$row.remove();
});
});
Notice that we aren't using Bootstrap's HTML attributes to load up the modal anymore. Bootbox is creating the modal for us.
With Vanilla Bootstrap/jQuery
To do this with straight Bootstrap, I would again not use the Bootstrap HTML attributes to directly load up the modal. Something like the following would work. Notice it's not as clean, but this could easily be cleaned up depending on how your JavaScript is setup.
var $row = null;
$(document).on('click', '.delete', function(e){
e.preventDefault();
$row = $(this).closest('tr');
$('#deleteCard').modal();
});
$(document).on('click', '.submitDelete', function(e){
e.preventDefault();
if($row != null) { $row.remove(); $row = null; }
});
One way of cleaning this up would be to put the card id on a data attribute of the modal. It removes the need to store it in a variable somewhere else. Again, cleaning this up requires looking in-depth into what your JavaScript looks like. Good luck.
This is your anchor element <a>:
var test = $("#cards table tr .delete[data-id='"+card_id+"']");
Though it can be shortened. As this will refer to the anchor that was clicked inside the function passed to the on() method. To make it a jQuery object you will need to pass this to $, $( this );.
Now you need to traverse up through the DOM to the table row <tr>. jQuery provides a method called closest() to do this.
var link = $( this );
var tr = link.closest( 'tr' );
// Do what you need to with variable tr.

How to jump the control to an option in a dropdown list by just pressing the first letter of it from the keyboard?

Following is the html code I am using to create a dynamic list of VF pages along with the Jquery function I am using to achieve the functionality.I found that using the keypress element would help me in achieving the requirement which I am looking for, but it does not work.
HTML CODING
<div id="VFPageListsDropDown">
<span></span>
<button type="button" data-toggle="dropdowns" data-dropdowns="#dropdowns-1" class="btn btn-primary dropdowns-toggle" id="btnSort" >
<table width="100%">
<tr>
<td width="81%" id="BtnDropDown">Select VF Pages</td>
<td width="19%"> <span class="caret"></span></td>
</tr>
</table>
</button>
<span>
<div id="dropdowns-1" class="dropdowns dropdowns-tip">
<ul class="dropdowns-menu" id="VFPageListsDropDown"></ul>
</div>
</span>
</div>
Jquery function:
$('#').on('shown.bs.dropdown', function () {
var $this = $(this);
// attach key listener when dropdown is shown
$(document).keypress(function(e){
// get the key that was pressed
var key = String.fromCharCode(e.which);
// look at all of the items to find a first char match
$this.find("li").each(function(idx,item){
$(item).removeClass("active"); // clear previous active item
if ($(item).text().charAt(0).toLowerCase() == key) {
// set the item to selected (active)
$(item).addClass("active");
}
});
});
// unbind key event when dropdown is hidden
$('#').on('hide.bs.dropdown', function () {
$(document).unbind("keypress");
})
Please suggest me if there is any solution for it...

Dynamic HTML IDs (PHP, Java, and a bit of SQL)

I'm trying to create a web page which generates a series of unique DIV IDs, each displaying different content based off of the entries in an SQL table.
Each div has a "hide" and "show" button, which work independently when manually giving each div a unique name.
I can get the divs themselves to generate based on class names in PHP, which displays the divs correctly.
The problem lies in the "hide" and "show" buttons since they're controlled by JavaScript. The code is as follows:
for ($j = 0 ; $j < $rows ; ++$j)
{
for($i =0; $i < $rows2; $i++)
{
if (mysql_num_rows($ans) > 0) //check if widget table is empty
{
$widgetusr[$j] = mysql_result($ans,$j,'wname')or die(mysql_error()); //user's widget
$widgetstore[$i] = mysql_result($ans2,$i,'wname'); //store widget
if($widgetusr[$j] == $widgetstore[$i] && $widgetusr[$j] != 'Medieval Calendar') //check if user has already purchased the widget
{
echo "<div class=widget_container".$j%2 .">"; //container divs are named 1 and 0. j mod 2 should return either 1 or 0
?>
<!----Start of weather Widget--->
<!---Script for show/hide buttons weather widget--->
<script>
var widg = "<?php echo $widgetusr[$j]; ?>";
var id = "#" + widg;
$(document).ready(function(){
$("#hide1").click(function(){
$(id).hide();
});
$("#show1").click(function(){
$(id).show();
});
});
</script>
<button id="hide1">Hide</button>
<button id="show1">Show</button>
<!---End Script for show/hide buttons weather widget--->
<?php
echo "<div class = 'widget' id='$widgetusr[$j]'>
</div>
</div>
<!----End of Widget---> ";
}
}
else
{
echo "You have no widgets please visit <a href='store.php'> the store </a> to purchase some. <br/>"; //widget table is empty. Redirect to widget store.
}
}
}
?>
I tried to pass the php varriable (containing an SQL value) to JavaScript (which works successfully, I was able to print out "#financial widget" as an id name.), however neither the show, nor hide button works. The generated divs all have the correct names also.
If additional information is required please ask. I tried to be as general as possible.
You really only need one button. Change your php to render the following html
<div class="widget_container">
<button class="btn ">Hide</button>
<div class="widget">widget1</div>
</div>
<div class="widget_container">
<button class="btn">Hide</button>
<div class="widget">widget2</div>
</div>
<div class="widget_container">
<button class="btn">Hide</button>
<div class="widget">widget3</div>
</div>
and output the following Outside of the loop, ensuring jQuery is loaded:
<script type="text/javascript">
//Standar jquery doc ready event, fires when the dom is loaded
$(document).ready(function(){
//add an event listener elements with a class of "btn"
$('.btn').click(function () {
//"this" is the element click, so we find siblings of this with a class
//of "widget" and toggle its visibility
$(this).siblings('.widget').toggle();
//Change the text of the button the below is short hand for:
//if($(this).text() == "Hide"){
// $(this).text("Show");
//}else{
// $(this).text("Hide");
//}
$(this).text($(this).text() == "Hide" ? "Show" : "Hide");
});
});
</script>
Example
Some useful links:
http://learn.jquery.com/using-jquery-core/document-ready/
http://api.jquery.com/click/
http://api.jquery.com/siblings/
http://api.jquery.com/closest/
http://api.jquery.com/toggle/
http://api.jquery.com/text/
https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Conditional_Operator
Example with fixed height widgets: http://jsfiddle.net/bdpm4/2/
Update 2
Perhaps a better way to do it: http://jsfiddle.net/bdpm4/3/
you should use class instead of id and dont put your $(document).ready() in the loop.
HTML:
<div class="widget_container">
<button class="btn hideBtn">Hide</button>
<button class="btn showBtn">Show</button>
<div class="widget">widget1</div>
</div>
<div class="widget_container">
<button class="btn hideBtn">Hide</button>
<button class="btn showBtn">Show</button>
<div class="widget">widget2</div>
</div>
JS:
$(document).ready(function(){
$('.btn').on('click', function (evt) {
var btn = $(evt.target);
btn.siblings('.widget').toggle();
btn.parent().find('.btn').toggle();
});
});
CSS:
.showBtn {
display:none;
}
here is an example: http://jsfiddle.net/xdA4r/4/

Categories

Resources