I create some div dynamically and then i would click on one of them and show an alert. But it doesn't go. The div are into another big div that cointain them; if i click on the big div it's ok, but if i change the click event it doesn't go.
Big div:
<div id="combination"> </div>
With this function i create dynamically div (combinationCardID cointains ID of image that i want show in this div):
function showCombinationCard() {
var i, j;
for (i=0; i<combinationCardID.length; i++) {
$("#combination").append("<div id='c" + i + "' class='combcard'> </div>");
for (j=0; j<combinationCardID[i].length; j++) {
var image = $("#" + combinationCardID[i][j]).children("img").clone();
$("#c" + i).append(image);
$("#c" + i).append(" ");
}
}
And this is the click event (if i change .combcard with #combination it's ok, but this not):
$(".combcard").click(function() {
divID = $(this).attr("id");
alert("ok" + divID);
})
Use event delegation
$("#combination").on('click', '.combcard', function() {
divID = $(this).attr("id");
alert("ok" + divID);
})
Related
I am building a user interface with javascript and some jquery that is populated by a for loop from an array of products and their individual details. Once the products load with the abridged details, I want the user to be able to click on a 'details' button that will have make a pop up window appear showing the full details of the selected item. I have everything working HOWEVER the window is populated by the last item created by the for loop, as opposed to those of the item selected. I am pretty new to javascript and haven't been able to find any solutions that would fit this problem. Any ideas on how to accomplish this?
document.body.onload = addElement;
function addElement () {
for(i = 0; i < items.length; i++) {
//Create elements for items and pop windows, and html for individual item details
var prodDiv = document.createElement("div");
var popDiv = document.createElement("div");
// Add the rest of the html and looped data to variables
var popUpWindow = "<div class='popup-content'>" + divName + divPrice + divBrand + rating + prodId + divLong + "</p><button class='close'>Close</button></div></div>";
var blob = divImage + divName + divPrice + divBrand + divShort;
//Account for null values
if(items[i].brand == null) {
if(items[i].salePrice == null) {
var blob = divImage + divName + divPrice + divShort + dtlButton;
} else {
var blob = divImage + divName + divSale + divShort + dtlButton;
}
} else {
if(items[i].salePrice == null) {
var blob = divImage + divName + divPrice + divBrand + divShort + dtlButton;
} else {
var blob = divImage + divName + divSale + divBrand + divShort + dtlButton;
}
}
//Add item info to HTML element
prodDiv.innerHTML = blob;
popDiv.innerHTML = popUpWindow;
//Add class attributes
prodDiv.setAttribute("class", "col-sm-4 col-lg-2 prodContent");
popDiv.setAttribute("class", "popup-overlay");
//Add new element to div
var currentDiv = document.getElementById("allDiv");
currentDiv.appendChild(prodDiv);
currentDiv.appendChild(popDiv);
//Appends an "active" class to .popup and .popup-content when
the "Open" button is clicked
$(".open").on("click", function(){
$(".popup-overlay, .popup-content").addClass("active");
});
//Removes the "active" class to .popup and .popup-content when
the "Close" button is clicked
$(".close, .popup-overlay").on("click", function(){
$(".popup-overlay, .popup-content").removeClass("active");
});
}};
There're some problem.
You bind event in for loop, and event is bind for a class selector => all exists button will be binded again.
It's mean, if you have 10 item, first button will call 10 times click funtion.
You should move them outside for loop, or change selector.
And you must tell jquery exactly popup to show when you click a button
You can change like that:
1: add some thing to identify popup
var popUpWindow = "<div class='popup-content itemid-"+ yourItemId +"'>"
2: Then, bind to only right button
$(prodDiv).find(".open").on("click", function(e){
//do smthing to show right div,
// $(".itemid-"+yourItemId ) .....
});
and fix close button, too
Suppose I have a parent div which contains two more div which are created dynamically using jQuery. When I click on div one then it will alert or console its id value if I clicked on the second div then it will show the second div id attribute value
for (i=0; i < 3; i++){
content = "<div class='dataToAppend' id="+i+" style='cursor:pointer; margin:30px; display:inline-block;'>"
content += '<img id='+i+' src='+i+' >'
content += "</div>"
$(".data").append(content)
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.2.1/jquery.min.js"></script>
<div class="data"></div>
In this snippet when I click on one image then I want it console its id attribute
You can bind a delegated click event to the images:
for (i = 0; i < 3; i++) {
content = "<div class='dataToAppend' id='div" + i + "' style='cursor:pointer; margin:30px; display:inline-block;'>"
content += '<img id=' + i + ' src=' + i + ' >'
content += "</div>"
$(".data").append(content)
}
$(".data").on('click', 'img', function() { // use a delegated event on the image
console.log(this.id); // this is the image id
console.log($(this).parent().attr('id')); // this is the div id
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.2.1/jquery.min.js"></script>
<div class="data"></div>
Please note that ids should be unique and you currently have your div and image ids being created the same, I edited above so they are different
Capture the click event in its bubbling phase on the .test element, check the event target, and, if it's a div then get the id else if it's an image get the id of its parentNode.
You may use vanillaJS for this task
document.querySelector('.test').addEventListener('click', function(ev) {
let tgt = ev.target;
if (tgt.matches('div')) {
console.log(tgt.id);
}
if (tgt.matches('img')) {
console.log(tgt.parentNode.id);
}
});
(As a side note, your id can't start with a digit)
With vanilla JavaScript, you can just query all three .dataToAppend divs after the for loop and use the forEach() method to return the id of each element.
Check and run the following Code Snippet for a practical example of what I have described above:
var data = document.querySelector(".data");
for (i=0; i < 3; i++){
content = "<div class='dataToAppend' id=imgDiv"+i+" style='cursor:pointer; margin:30px; display:inline-block;'>";
content += '<img id='+i+' src=img'+i+' >';
content += "</div>";
data.innerHTML += content;
}
var dataDivs = document.querySelectorAll(".dataToAppend");
dataDivs.forEach(div => {
div.addEventListener("click", () => console.log(div.id));
});
<div class="data"></div>
N.B. In the above example, I have appended a non-numeric character for easier element targeting in CSS.
You can use:
$(document).on('click', '.dataToAppend img', function() {}
To add a click event to all your imgaes within the div with the class .dataToAppend.
Next, you can use $(this).attr('id'); to get the id of the image you clicked on.
Also, I suggest you build up a string called content in your for loop (as .append() is a somewhat expensive method to run), and only once that is complete you .append() the content to your DOM. This way you are only adding to the DOM once, rather than multiple times.
See working example below:
let content = "";
for (i = 0; i < 3; i++) {
content += "<div class='dataToAppend' id=" + i + " style='cursor:pointer; margin:30px; display:inline-block;'>"
content += '<img id=' + i + ' src=' + i + ' >'
content += "</div>"
}
$(".data").append(content);
$(document).on('click', '.dataToAppend img', function() {
let id = $(this).attr("id");
console.log(id);
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.2.1/jquery.min.js"></script>
<div class="data"></div>
The below images are all returned and displayed on page via this JavaScript/jQuery:
for(var j = 0; j < imageURLs.length; j++){
$('#imgs').append("<img src='" + imageURLs[j] + "'/>");
$('#username').append(Username[j]);
}
HTML:
<div id="imgs"></div>
I want the user to be able to click on any of the images and pass the image/username into a variable.
I thought I could use $this to select the individual images/usernames, but that just seems to return "imgs" each time. How can I use jQuery to select and capture the actual username/images? Do I need to use .mouseover() before adding the item?
$('imgs').click(function(event){
event.preventDefault();
var selectedFriend = $(this).attr("id");
console.log(selectedFriend);
});
});
Your selector is incorrect. When you are using $('imgs') jQuery is searching for imgs element which doesn't exists. Thus you need to change your selector to ID selector
Apart from above you are creating img element dynamically, thus you need to use Event Delegation
$('#imgs').on('click', 'img', function (event) {
event.preventDefault();
var selectedFriend = $(this).attr("id");
console.log(selectedFriend);
});
You could try having the append to define the onclick event too.
$('#imgs').append("<img src='" + imageURLs[j] + "' onclick='doStuff(this)'/>");
Try the following (not tested):
for(var j = 0; j < imageURLs.length; j++){
$('#imgs').append("<img src='" + imageURLs[j] + "' id='PUT_YOUR_UNIQUE_ID_HERE' />");
$('#username').append(Username[j]);
}
$('imgs').on('click', 'img', function(event){
event.preventDefault();
var selectedFriend = $(this).attr("id");
console.log(selectedFriend);
});
I have a website with 2 links.
Once a user clicks a link, this has to become a h2 title without a link.
When the user clicks on the second link, the first links must be restored to its previous state and the second link should become a h2 element.
The links have the purpose of showing a new tab, so they do not reload the page.
HTML (don't mind the href link)
<div id="Panel" class="header-panels">
<a data-linked="#panelImages" href=".../images/#" tabindex="0" class="active">Foto's</a>
<a data-linked="#panelVideos" href=".../videos/#" tabindex="0">Video's</a>
</div>
Is there anyway to do this with javascript/jquery?
I have tried stuff like:
var p = $('.header-panels .active');
var a = $('<h2></h2>').append(p.contents());
p.replaceWith(a);
And it works to change the a tag into h2, but I cannot seem to recreate the a tag with all the attributes when a users clicks a second time.
Or does anyone know a better approach on this?
Thanks in advance?
Fiddle Demo
var all_a = $('#Panel a'); //cache your selector
var h2 = $('<h2/>').attr('id', 'temp');//created a h2 tag with id temp (just for identification if u need to style it)
all_a.click(function (e) {
e.preventDefault();//stop default behavior of click if u want
all_a.show(); //show all a tag inside id Panel
var $this = $(this); //cache selectore
h2.text($this.text()).insertBefore($this); //insert h2 before current a tag clicked and with it's text
$this.hide(); //hide clicked a
});
.insertBefore()
This script let you toggle 'h2' and 'a' without adding third element, it just replace 'h2' with a 'a' element, and add all the parameters of 'a' element to the 'h2' element on the form of data.
$(document).on('click', '#Panel a', function (e) {
e.preventDefault();
$this = $(this);
var $h2Elem = $this.parents('#Panel').find('h2');
console.log($h2Elem);
$h2Elem.each(function (index, item) {
var linked = $(item).data('linked'),
href = $(item).data('href'),
tabindex = $(item).data('tabindex'),
text = $(item).text();
$(item).replaceWith('<a data-liked="' + linked + '" href="' + href + '" tabindex="' + tabindex + '">' + text + '<a>');
});
var linked = $(this).data('linked'),
href = $(this).attr('href'),
tabindex = $(this).attr('tabindex'),
text = $(this).text();
$this.replaceWith('<h2 data-liked="' + linked + '" data-href="' + href + '" data-tabindex="' + tabindex + '">' + text + '<h2>');
});
Fiddle HERE
why don't you use separate elements and hide/show them as required? E.g.
<div id="Panel" class="header-panels">
<a data-linked="#panelImages" href=".../images/#" tabindex="0" class="active" id="fotolink">Foto's</a><h2 id="foto" style="display: none;">Foto's</h2>
<a data-linked="#panelVideos" href=".../videos/#" tabindex="0" id="videolink">Video's</a><h2 id="video" style="display: none;">Video's</h2>
</div>
<script type="text/javascript">
$("#fotolink").on("click", function (e) {
$("#fotolink").hide();
$("#foto").show();
$("#videolink").show();
$("#video").hide();
//e.preventDefault();
});
$("#videolink").on("click", function (e) {
$("#fotolink").show();
$("#foto").hide();
$("#videolink").hide();
$("#video").show();
//e.preventDefault();
});
</script>
EDIT:
In light of your comment, I would then store the reference to the old anchor element and use detach(). E.g.
var oldLink;
function removeH2() {
var h2 = $("#textheading");
if(h2) {
$(oldLink).insertBefore(h2);
$(h2).remove();
}
}
function toText(a) {
oldLink = a;
var h2 = $('<h2 id="textheading">' + $(a).text() + '</h2>');
$(h2).insertAfter(a);
$(a).detach();
}
$("#fotolink").on("click", function (e) {
//e.preventDefault();
removeH2();
toText(e.target);
});
$("#videolink").on("click", function (e) {
//e.preventDefault();
removeH2();
toText(e.target);
});
Given this fiddle, what is preventing the HTML from being rendered?
JavaScript
$(document).ready(function(){
function loadDiv( divId ) {
$('#' + divId).html('<table><tr><td class="editable" id="' + divId + '">Edit Me</td></tr></table>');
}
$('td.editable').click(function() {
var cellId = $('td.editable').attr('id');
alert(cellId);
});
loadDiv( div1 );
loadDiv( div2 );
});
My intention is to change the clicked cell into an input field and later post from it, but I'm not sure why it's not rendering.
You need to add quotes around your div ids.
loadDiv( "div1" );
loadDiv( "div2" );
http://jsfiddle.net/pp6nv/1/
Since the tables are added after the page loads, you'll have to use .on().
$('body').on("click", "td.editable", function() {
var cellId = $(this).prop('id');
alert(cellId);
});
http://jsfiddle.net/pp6nv/3/