Modal not visible in Twitter boootstrap - javascript

I am trying to display a modal on image click with the image which is clicked, but its not working.
fiddle
I am inserting the content of modal after the user clicks the image using
$("#imageModal").html(modalHtml);
$('#imageModal').modal('show');
This code might now work as I am getting the error: showModal is not defined but the same code is working on my website.
Please help find the issue.

First at the very top of your html body....directly after the <body> tag, and before any content.
Put your modal...without any img, just an empty body...
<div id="imageModal" class="modal hide fade in">
<div class="modal-header"><a class="close" data-dismiss="modal">x</a>
<h3>Select the area</h3>
</div>
<div class="modal-body"></div>
<div class="modal-footer">
Men Topwear
Men Bottowear
Women Topwear
Women Bottomwear<br>
Close
</div>
Then later in your document, wherever you want the images...just wrap them in a <a> tags, and apply the name of the modal box to the href, and apply the data-toggle attribute... data-toggle="modal"
<a class='galleryImg' href="#imageModal" data-toggle="modal">
<img src="http://media.santabanta.com/gallery/global%20celebrities(f)/shakira/shakira-28-m.jpg" />
</a>
<a class='galleryImg' href="#imageModal" data-toggle="modal">
<img src="http://media.santabanta.com/gal/event/ramaiya-vastavaiya-sp" />
</a>
Then in your Jquery...simply find all the links with the class .galleryImg, or however you want to identify them, and apply a click handler...that passes the image, to the modal.
$('a.galleryImg').click(function (e) {
e.preventDefault();
var img = $(this).html();
$('.modal-body').html(img);
});
Heres the JSFIDDLE DEMO
UPDATE
After looking at the code you pasted....you cant do it like that, as you are outputting two click handlers, on created items. You need to do it like this...
function testAPI(){
listOfPage = ["http://media.santabanta.com/gallery/global%20celebrities(f)/shakira/shakira-28-m.jpg", "http://media.santabanta.com/gal/event/ramaiya-vastavaiya-special-screening/ramaiya-vastavaiya-special-screening-32.jpg"]
for (var i=0;i<listOfPage.length;i++){
$("#imgbox").append('<a class="galleryImg" href="#imageModal" data-toggle="modal"><img src="'+listOfPage[i]+ '"></a>');
}
}
And then sepereately have this outside of the loop....
$('body').on('click', 'a.galleryImg', function (e) {
e.preventDefault();
var img = $(this).html();
$('.modal-body').html(img);
});
Because since you are appending the items, they are dynamically created so you need to use on instead of click
But you also need to wrap it all in a $(document).ready(function()...like so
$(document).ready(function(){
//Facebook login function run/loop
function testAPI(){
listOfPage = ["http://media.santabanta.com/gallery/global%20celebrities(f)/shakira/shakira-28-m.jpg", "http://media.santabanta.com/gal/event/ramaiya-vastavaiya-special-screening/ramaiya-vastavaiya-special-screening-32.jpg"]
for (var i=0;i<listOfPage.length;i++){
$("#imgbox").append('<a class="galleryImg" href="#imageModal" data-toggle="modal"><img src="'+listOfPage[i]+ '"></a>');
}
}
//Apply click handler to dynamic links...
$('body').on('click', 'a.galleryImg', function (e) {
e.preventDefault();
var img = $(this).html();
$('.modal-body').html(img);
});
});

Related

How to addeventlistener to modal buttons in handlebars template

I am creating a web app that connects to a news API and shows articles.
For each article, I have created a card and a modal in handlebars.
Upon clicking the button on each respective card, I would like a modal to open with its unique information.
I am trying to add an event listener for the button on the card to open the modal.
<div class="">
{{!-- #each article --}}
<div class="row">
{{#each articles}}
<div class="col-12-sm col-6-md col-3-lg">
<div class="card m-2">
<div class="card-body">
<h5 class="card-title">{{title}}</h5>
<p class="card-text">{{description}}</p>
</div>
<img class="card-image" src="{{urlToImage}}" alt="Card image cap">
<button id="mybtn" class="{{#index}}">Open Modal</button>
{{#index}}
</div>
</div>
{{/each}}
</div>
</div>
{{#each articles}}
<!-- The Modal -->
<div id="modid" class="modal">
<!-- Modal content -->
<div class="modal-content">
<span class="close">×</span>
<p>Some text in the Modal..</p>
</div>
</div>
{{/each}}
<script>
let modal = document.getElementById("modid");
let btn = document.getElementById("mybtn");
let span = document.getElementsByClassName("close")[0];
btn.onclick = function() {
modal.style.display = "block";
}
span.onclick = function() {
modal.style.display = "none";
}
window.onclick = function(event) {
if (event.target == modal) {
modal.style.display = "none";
}
}
const btn = document.querySelector('.{{#index}}');
btn.addEventListener('click', function(event){
console.log('Button Clicked');
}
</script>
Clicking on the "Open Modal" button does nothing, nor does it give an error.
I am unsure if the button class {{#index}} is being read properly by the script.
Any assistance or tips would be greatly appreciated!
First, I think a better approach than using class="{{#index}} on each button would be to use a data-attribute, like data-open-modal="{{#index}}". This will allow us to use a query selector to get all of the open modal buttons as well as allow us to get the specific index in our click handler.
Next, we cannot use a single id for each of our modal elements as you are doing with id="modid". This leads to multiple elements with the same id, "modid", which is invalid HTML. Also, it prevents us from specifying which modal we want to open. Let's just remove that id.
In our JavaScript, we can select all of the open modal buttons and modals and store them in variables:
const openModalButtons = document.querySelectorAll('[data-open-modal]');
const modals = document.querySelectorAll('.modal');
Next, we can loop through all of openModalButtons and assign a click handler to each.
openModalButtons.forEach(openModalButton => {
openModalButton.addEventListener('click', (event) => {
const openIndex = Number(event.target.dataset.openModal);
modals.forEach((modal, index) => {
modal.classList.toggle('open', index === openIndex);
modal.classList.toggle('closed', index !== openIndex)
});
});
});
Notice that our click handler gets the data-open-modal index value from the button that was clicked. This is the index of the modal to show.
Next, it loops over each modal element and sets the "open" class if the index is equal to the index we want to show; otherwise, it sets the "closed" class.
I have created a fiddle for reference.
Update: To handle "close" button clicks:
The close button is very similar to the open button. You would need to attach an event listener and you would need a way to know which modal element to target. We could use a data-attribute again, like <button class="close" data-close-modal="{{#index}}">×</button>. Note: To be semantically correct, a close button should be a <button element, not a <span>.
Our click event listener for the close buttons would be very similar to that of the open buttons. This time, however, we won't loop through all of the modals; we will just update the modal whose index in the array of modal elements is equal to the data-close-modal attribute value of the clicked close button.
const closeModalButtons = document.querySelectorAll('[data-close-modal]');
closeModalButtons.forEach(closeModalButton => {
closeModalButton.addEventListener('click', (event) => {
const closeIndex = Number(event.target.dataset.closeModal);
modals[closeIndex].classList.remove('open');
modals[closeIndex].classList.add('closed');
});
});
Note: You may very well not require an .open and a .closed class for you modals - one may be sufficient. This is just an example.
An updated fiddle has been creeated.

Find sibling with Javascript and Hammer.js

I have made a simple system which detects double taps. I want to show a heart icon when someone double taps on an image, just like on Instagram.
This is what my code looks right now:
var elements = document.getElementsByClassName('snap_img');
[].slice.call(elements).forEach(function(element) {
var hammertime = new Hammer(element),
img_src = element.getAttribute('src');
hammertime.on('doubletap', function(event) {
alert(img_src); // this is to test if doubletap works
// Some javascript to show the heart icon
});
});
This is what the HTML looks like:
<div class="snap_item">
<div class="snap_item_following_info">
<img class="snap_item_following_img" src="res/stat/img/user/profile/small/1.fw.png" alt="#JohnDoe" />
<a class="snap_item_following_name" href="#">#JohnDoe</a>
<div class="snap_too">
</div>
</div>
<img class="snap_img" src="res/stat/img/user/snap/43/2.fw.png" alt="#ErolSimsir" />
<div class="like_heart"></div>
<div class="snap_info">
<div class="snap_text">
LA is the shit...
<a class="snap_text_hashtah" href="#">#LA_city_trip</a>
</div>
<div class="snap_sub_info">
<span class="snap_time">56 minutes ago</span>
<div class="like inactive_like">
<div class="like_icon"></div>
<div class="like_no_active">5477</div>
</div>
</div>
</div>
</div>
So when the element 'snap_img' is double tapped, I need to get the element 'like_heart' which is one line below the snap_img element. How do I get that sibling element and fade it in with JQuery?
Like this
[].slice.call(elements).forEach(function(element) {
var hammertime = new Hammer(element),
img_src = element.getAttribute('src');
hammertime.on('doubletap', function(event) {
alert(img_src); // this is to test if doubletap works
$(element).next().text('♥').hide().fadeIn();
});
});
P.S. I've added that heart text, since the sibling was empty.
On the event handler, i would do $(element).parent().find('.like_heart').fadeIn(); So the code is not dependant on the element ordering.
(To clarify to selector: take the parent element which is the div.snap_item and find an element with class like-heart inside it)

Jquery Show Hide with attribute

How to get value from custom attribute to be used in if else condition?
I want to switch button between show & hide . if show button clicked it will hiden and the hide button showed. And also the same for opposites.
So i can do show hide for my divs.
Here's my codes
<div class="wrapper">
<a class="show_detail" target="1" style="display:block">+ Show</a>
<a class="hide_detail" target-hide="1" style="display:none">- Hide</a>
<div class="event_down" id="event_down1" style="display:none">
Content 1
</div>
<a class="show_detail" target="2" style="display:block">+ Show</a>
<a class="hide_detail" target-hide="2" style="display:none">- Hide</a>
<div class="event_down" id="event_down2" style="display:none">
Content 2
</div>
<a class="show_detail" target="3" style="display:block">+ Show</a>
<a class="hide_detail" target-hide="3" style="display:none">- Hide</a>
<div class="event_down" id="event_down3" style="display:none">
Content 3
</div>
</div>
CSS:
.show_detail{cursor:pointer; color:red;}
.hide_detail{cursor:pointer; color:red;}
JS :
$('.show_detail').click(function(){
var atribut_show = $('.show_detail').attr('target');
var atribut_hide = $('.hide_detail').attr('target-hide');
if (atribut_show == atribut_hide){
$('.hide_detail').show();
$(this).hide();
}
$('.event_down').hide();
$('#event_down'+$(this).attr('target')).show();
});
and here's MY FIDDLE need your help to solve it.
in order to get custom attributes their name must start with "data-". For example your custom attribute target would be "data-target". After that you can get them using something like $("#myElement").getAttribute("data-target").
You are getting object array list you have to get only the current object
Check updated fiddle here
"http://jsfiddle.net/p7Krf/3/"
$('.show_detail').click(function(){
var atribut_show = $(this).attr('target');
$('.hide_detail').each(function(element){
if($(this).attr("target-hide")==atribut_show){
$(this).show();
}
});
$(this).hide();
$('#event_down'+atribut_show).show();
});
The following javascript made it function for me. You should however consider calling your attributes data-target and data-target-hide as your specified attributes are not actually valid. It will function, but you could run into problems if you don't change the attribute names.
$('.show_detail').click(function(){
var atribut_show = $(this).attr('target');
$('.hide_detail[target-hide="'+atribut_show+'"]').show();
$(this).hide();
$('#event_down'+atribut_show).show();
});
$('.hide_detail').click(function(){
var atribut_hide = $(this).attr('target-hide');
$('.show_detail[target="'+atribut_hide+'"]').show();
$(this).hide();
$('#event_down'+atribut_hide).hide();
});

If href equals id of another div do function

I have a hidden div with the details of a thumbnail that is visible on the page. When you click on the thumbnail, it should fadein or slideup the div with details.
I have set with jquery incremented ID's to each ".portfolio-item-details" to identify each one and then have set with jquery the same ID's to the href of the thumbnail.
<section id="portfolio1" class="portfolio-item-details hidden">content</section>
<a class="open-portfolio-item-details" href="#portfolio1" title="">
<img src="thumbnail.jpg">
</a>
<section id="portfolio2" class="portfolio-item-details hidden">content</section>
<a class="open-portfolio-item-details" href="#portfolio2" title="">
<img src="thumbnail.jpg">
</a>
Since this is done dynamically, how can I with jquery fadeIn or slideUp the ".portfolio-item-details" if the href is equal to the ID. Basically thumbnail with "#portfolio1" should slide up the div with "#portfolio1" on click.
This is my jquery code which to add the IDs and HREF is working perfectly but not working to slideUp or fadeIn the div with the same ID.
$(document).ready(function () {
var i=0;
$(".portfolio-item-details").each(function(){
i++;
var newID="portfolio"+i;
$(this).attr("id",newID);
$(this).val(i);
});
var i=0;
$(".open-portfolio-item-details").each(function(){
i++;
var newReadMoreHREF="#portfolio"+i;
$(this).attr("href",newReadMoreHREF);
$(this).val(i);
if ($(".portfolio-item-details").attr("id") == "newReadMoreHREF") {
$(this).fadeIn();
}
});
});
SOLUTION
Thanks to Austin's code, I was able to modify it to work with mine.
Check here: http://jsfiddle.net/jdoimeadios23/xpsrLyLz/
You want something like this?
HTML
<div class="image" value="1">
<img src="thumbnail.jpg" />
</div>
<div id="portfolio1" class="details">details</div>
<div class="image" value="2">
<img src="thumbnail.jpg" />
</div>
<div id="portfolio2" class="details">more details</div>
JS
$(document).ready(function () {
$('.details').fadeOut(1);
$(".image").click(function () {
var num = $(this).attr("value");
$("#portfolio"+num).fadeIn(1000);
});
});
JSFiddle Demo
You don't even need to bother with ID's so long as the next div below each image is it's details.
The problem is in this block
if ($(".portfolio-item-details").attr("id") == "newReadMoreHREF") {
$(this).fadeIn();
}
Because you're having two errors, the first one is that newReadMoreHREF is a variable, not a string in your HTML or a value to any variable and so on.
Second thing is, that in the variable declaration you're using "#portfolio"+i;, which would be good if you were about to select an element. But using it in the jQuery iif statement with .attr('id') will again cause a havoc.
The thing that you need is something like this
$(".open-portfolio-item-details").each(function(){
i++;
var newReadMoreHREF="portfolio"+i; // removed #
$(this).attr("href",newReadMoreHREF);
$(this).val(i);
if ($(".portfolio-item-details a").attr("id") == newReadMoreHREF) {
// you need to access the hyperlink in the element, not
// the element itself. this portfolio1 ID is of a hyperlink
// again here, this is referencing the main iterator.
$(this).fadeIn();
// are you sure you want to fade the .open-portfolio-item-details?
}
});
Removed the hash sign and then called the variable value to check against. It would execute to be true if the condition is true.
Try this:
HTML:
content
<section id="portfolio2" class="portfolio-item-details hidden">content</section>
<a class="open-portfolio-item-details" href="#portfolio2" title="">
<img src="thumbnail.jpg">
</a>
<div id="portfolio1" class="portfolio" hidden>Portfolio 1</div>
<div id="portfolio2" class="portfolio" hidden>Portfolio 2</div>
Jquery:
$('a.open-portfolio-item-details').on('click', function (e) {
e.preventDefault();
var id = $(this).attr('href');
$('.portfolio').hide();
$('.portfolio' + id).fadeIn();
});
Couldn't get the fiddle link for some reason.
Edit:
I don't know the name of the class that shows the content you want displayed, so as an example I'm using portfolio. Try putting this code into a fiddle

Show a div when a mouseover on a link

If I mouseover on a link it has to show div.
My problem is that I have to show divs in all of the links inside a page. For each link I have to show a different div.
How to do this using javascript?
Since, your question does not specify anything. I will give a simplest solution I can. That is, with plain CSS, no JS needed.
Here is a demo
Markup
<a href="#">
Some
<div class="toshow">
Hello
</div>
</a>
<a href="#">
None
<div class="toshow">
Hi
</div>
</a>
CSS
.toshow {
display:none;
position: absolute;
background: #f00;
width: 200px;
}
a:hover div.toshow {
display:block;
}
You should not try to rely on script as much as possible. This is a very simple example, with displays the use of :hover event of the link.
Steps can be:
Make multiple divs all with different id.
Give style="display:none;" to all div.
Make links to show respective div.
In onMouseOver of link call js function which changes display property to block of proper div. Ex.:- document.getElementById("divId").style.display = "block"; And for all other div set display:none; in that js function.
Sample code:-
Your links:
Div 1
Div 1
Your divs:
<div id="myDiv1">Div 1</div>
<div id="myDiv2">Div 2</div>
JS function:
function Changing(i) {
if(i==1){
document.getElementById("myDiv1").style.display = "block";
document.getElementById("myDiv2").style.display = "none";
} else {
document.getElementById("myDiv1").style.display = "none";
document.getElementById("myDiv2").style.display = "block";
}
}
If you have more divs then you can use for loop in js function instead of if...else.
look at jquery each
<div id=div-0" class="sidediv" style="display:none" > Div for first link </div>
<div id=div-1" class="sidediv" style="display:none"> Div for second link </div>
<div id=div-2" class="sidediv" style="display:none"> Div for third link </div>
<a class="linkclass" href=""> Link </a>
<a class="linkclass" href=""> Link </a>
<a class="linkclass" href=""> Link </a>
and essentially do something like this
$('.linkclass').each(function(i,u) {
$(this).hover(function()
{
$('#div-'+i).show();
}, function() {
$('#div-'+i).hide(); //on mouseout;
})
});
Edit: oops ...this will need jquery. dont know why I assumed jquery here.
You can give ids to all the links such as
<a id="link-1"></a>
<a id="link-2"></a>
<a id="link-3"></a>
and so on ..
and similarly to div elements
<div id="div-1"></div>
<div id="div-2"></div>
<div id="div-3"></div>
and so on ..
then
$("a").hover(function () { //callback function to show on mouseover
var id = $(this).attr('id').replace("link-", "");
$("#div-"+id).show();
},
function () { //if you want to hide on mouse out
var id = $(this).attr('id').replace("link-", "");
$("#div-"+id).hide();
}
);

Categories