Work with appended audio - javascript

i have trouble with appended audio.
when page is scrolling i'm dynamicly load an audio, but then, when i'm trying to play it, div, in which located audiofile isn't changing it's property, how to solve that?
How i appending:
$(window).scroll(function(){
if(scrollCount == 0){
if($(window).scrollTop() > 200){
AddMoreContent();
}
} else{
if($(window).scrollTop() > $(window).height() * scrollCount - 100) {
AddMoreContent();
}
}
});
function AddMoreContent(){
$.ajax({url:thisPage + "/" + thisPage + "." + scrollCount +".html",context: document.body, success: function(response){
$("#main-content").append(response);
scrollCount++;
}
});
}
How i listening audio event:
$(document).ready(function () {
$("audio").on("play", function () {
var _this = $(this);
//$("audio").each(function (i, el) {
// if (!$(el).is(_this))
// $(el).get(0).pause();
// $(el).parent().removeClass("intro");
//});
_this.parent().addClass("intro");
});
});

The play event does not bubble, So you can't use event delegation. You need to bind the handler once the element is added to the dom so
function AddMoreContent() {
$.ajax({
url: thisPage + "/" + thisPage + "." + scrollCount + ".html",
context: document.body,
success: function (response) {
var $els = $(response);
$("#main-content").append($els);
//use .filter if the audio elements are in the root level of response
$els.find("audio").on('play', function () {
//do your stuff
});
scrollCount++;
}
});
}

Assuming the audio elements are appended through the $.ajax requests, you need to use a delegated event handler:
$('#main-content').on('play', 'audio', function() {
$(this).parent().addClass('intro');
// your code here...
});

Related

jQuery - preventDefault() in .each function

I want to use preventDefault() in .each function for collection of buttons and its not working. When I use it with one .click function it works fine but inside .each is not
Whan am I doing wrong?
Here is my .js code
$(document).ready(function() {
var findingStatus = $('#findingStatus').attr('finding-status-type');
var findingLike = $('#finding_like_btn');
var findingDislikeBox = $('.finding_dislike_add');
var findingDislikeCollection = $('.finding_dislike_add_btn')
var findingUnlike = $('#finding_unlike_btn');
var findingDislikeRemoved = $('#finding_dislike_removed');
var alertBox = $('.alert-box').hide();
if (findingStatus == 0) {
findingDislikeBox.show();
findingUnlike.hide();
findingDislikeRemoved.hide();
}
else if (findingStatus == 1) {
findingDislikeBox.hide();
findingUnlike.show();
findingDislikeRemoved.hide();
}
else if (findingStatus == 2) {
findingDislikeRemoved.show();
findingUnlike.show();
findingDislikeBox.hide();
findingLike.hide();
}
findingDislikeCollection.each(function() {
var findingDislike = $(this).clone();
var url = findingDislike.attr("href");
findingDislike.click(function(event) {
event.preventDefault();
$.ajax({
url: url,
type: "POST",
dataType: "json",
success: function(data) {
if (data.profileState == 1) {
$('#dislike_count_btn').text('Odrzuć' + data.DislikeCount);
findingDislikeBox.hide();
findingDislikeRemoved.show();
findingUnlike.show();
//findingUnDislike.show();
//findingUnDislike.attr('disabled', false );
//findingUnDislike.text('Cofnij');
}
else {
alertBox.show();
if ($('.alert-box-msg').length==0) {
$('.alert-area').prepend('<p class="alert-area alert-box-msg">Żeby korzystać z tej funkcji musisz być zalogowany.</p>');
}
findingDislike.attr('disabled', false );
}
},
error: function() {
alert('Problem z serwerem, spróbuj ponownie za kilka minut.');
findingDislike.attr('disabled', false );
}
});
});
});
$('html').click(function (e) {
if (!$(e.target).hasClass('alert-area')) {
$('.alert-box').hide();
findingDislike.attr('disabled', false );
}
});
});
Thanks for answer
You are cloning the element with .clone which means you're not actually attaching an event listener to anything in the DOM. Cloned elements must be manually inserted into the DOM with JavaScript for them to have any effect.
This is not a correct way. Following should work:
findingDislikeCollection.click(function(event){
var findingDislike = $(this);
var url = findingDislike.attr("href");
//AJAX call
event.preventDefault();
});
More details on click event are given here:
https://api.jquery.com/click/

Infinite Scroll with JScrollPane in Wordpress

I've done AJAX post loaders before but I'm having quite an hard time with jScrollPane.
Two things:
where should I load the posts? the div i created (#reviewspostscont) or .jspPane that JScrollPane makes? what if i have multiple loops then?
a more practical one now, this is the code i have so far, I can't get the function that triggers the AJAX to get the isAtRight variable (undefined in console), any fix?
Thanks in advance, Matt
$(function() {
$('#reviewspostscont').each(function() {
$(this).bind(
'jsp-scroll-x',
function(event, scrollPositionX, isAtLeft, isAtRight) {
console.log('Handle jsp-scroll-x', this,
'scrollPositionX=', scrollPositionX,
'isAtLeft=', isAtLeft,
'isAtRight=', isAtRight);
}
);
$(this).jScrollPane({ horizontalDragMaxWidth: 100 });
var api = $(this).data('jsp');
var throttleTimeout;
$(window).bind('resize', function() {
if (!throttleTimeout) {
throttleTimeout = setTimeout(function() {
api.reinitialise();
throttleTimeout = null;
}, 50);
}
});
});
$('#reviewspostscont').scroll(function() {
var $this = $(this);
var scrollWidth = $this[0].scrollWidth - $this.width();
var scrollPercentage = $this.scrollLeft() / scrollWidth * 100;
if (isAtRight == true) {
loadArticle(count);
count++;
}
});
function loadArticle(pageNumber) {
$.ajax({
url: "<?php bloginfo('wpurl') ?>/wp-admin/admin-ajax.php",
type:'POST',
data: "action=infinite_scroll&page_no="+ pageNumber + '&loop_file=loop',
success: function(html) {
$("#reviewspostscont").append(html); // This will be the div where our content will be loaded
}
});
return false;
}
});

Calling a plugin .on() load using jQuery

I am calling some jQuery plugins that attaches themselves to element on DOM ready. These plugins manipulate the DOM when certain events has occurred (click, change etc,)
$("body").find("input[type='checkbox']").checkbox();
Above works fine on DOM ready. However, if I'm loading some HTML from an AJAX call I have to use .on() to guarantee events gets bound consistently.
The question is which event I should bind the plugin to? I have tried below and it doesn't seem to respond.
$("body").on("load", "input[type='checkbox']", function(){
$(this).checkbox();
});
Here's the checkbox() plugin I'm referring to above. If that's any help. :)
'use strict';
define(['jquery'], function($){
return function(){
$.fn.checkbox = function (options) {
options = options || {};
var defaults = {
'className': 'jquery-checkbox',
'checkedClass': 'jquery-checkbox-on'
};
var settings = jQuery.extend(defaults, options);
return this.each(function () {
var self = jQuery(this);
var replacement = jQuery(
'<span class="' + settings.className + '-wrapper">' +
'<a class="' + settings.className + '" href="#" name="' + self.attr('id') + '"></a>' +
'</span>');
var element = jQuery('a', replacement);
if (self.prop('checked')) {
element.addClass(settings.checkedClass);
}
element.on('click', function (event) {
event.preventDefault();
event.stopPropagation();
var input = jQuery('input#' + jQuery(this).attr('name'), replacement.parent());
if (input.prop('checked')) {
input.removeAttr('checked');
} else {
input.prop('checked', true);
}
input.trigger('change');
return false;
});
element.on('focusin', function (event) {
$(this).addClass('checkbox-focus');
});
element.on('focusout', function (event) {
$(this).removeClass('checkbox-focus');
});
element.on("keypress", function(e){
if ( e.which === 32 ){ self.prop('checked', !self.prop('checked')).change(); }
});
self.on('change', function (event) {
var input = jQuery(this);
if (input.prop('checked')) {
jQuery('a[name=' + input.attr('id') + ']', replacement.parent()).addClass(settings.checkedClass);
} else {
jQuery('a[name=' + input.attr('id') + ']', replacement.parent()).removeClass(settings.checkedClass);
}
return true;
});
self.css({
'position': 'absolute',
'top': '-200px',
'left': '-10000px'
}).before(replacement);
});
}
};
});
You appear to want to apply add-ins to elements that have been loaded dynamically. That is not what 'on' is for.
Delegated events listen for specific events (like "click") at a parent/ancestor element then filter the possible recipients, then executes the supplied function against any matching elements that caused the event.
You actually need to apply the add-in code after your Ajax load completes.
Example:
In the success part of your ajax load, apply the addin:
$("input[type='checkbox']").checkbox();
If you loaded a specific part of the screen (likely), then target the selector at that element:
e.g.
$("#myloadcontainer input[type='checkbox']").checkbox();

JQUERY 1.9 ,1.10, 1.11 conflict with code

I have this piece of code , that does not work , if I link JQUERY above 1.8.0
Just for curiosity, why its happening?
it takes values from select boxes, passing to pagination.php file and in the meantime showing loading image
// Pagination
$(document).ready(function () {
function loading_show() {
$('#loading').html("<img src='img/loading.gif'/>").fadeIn('fast');
}
function loading_hide() {
$('#loading').fadeOut('fast');
}
function loadData(page) {
var house_id = $("#pbthouse option:selected").val();
var sale_id = $("#pbtsale option:selected").val();
var year_id = $("#pbtsale option:selected").val();
var ipp = $("#res option:selected").val();
loading_show();
$.ajax({
type: "POST",
url: "pagination.php",
//data: "page="+page,
data: {
page: page,
house_id: house_id,
year_id: year_id,
sale_id: sale_id,
ipp: ipp
},
success: function (msg) {
$("#container1").ajaxComplete(function
(event, request,settings)
{
loading_hide();
$("#container1").html(msg);
});
}
});
}
loadData(1); // For first time page load default results
$('#container1 .pagination li.active').live('click', function () {
var page = $(this).attr('p');
loadData(page);
});
$('#go_btn').live('click', function () {
var page = parseInt($('.goto').val());
var no_of_pages = parseInt($('.total').attr('a'));
if (page != 0 && page <= no_of_pages) {
loadData(page);
} else {
alert('Enter a PAGE between 1 and ' + no_of_pages);
$('.goto').val("").focus();
return false;
}
});
$('#container1 .pagination li.active').live('click', function () {
var page = $(this).attr('p');
loadData(page);
});
$("#pbthouses").change(function () {
var page = '1';
loadData(page);
});
$("#res").change(function () {
var page = '1';
loadData(page);
});
$('#pbtsale, #pbtyear').change(function () {
var sale_id = $("#pbtsale option:selected").val();
var sale_id = $("#pbtyear option:selected").val();
var page = '1';
if (sale_id != '') {
$.ajax({
type: "POST",
url: "get_pbtsales.php",
data: {
year_id: year_id,
sale_id: sale_id
},
success: function (option) {
$("#pbhouses").html(option);
loadData(page);
}
});
} else {
$("#pbhouses").html("<option value=''
>-- No category selected --</option>");
}
return false;
});
});
Support for .live() has been deprecated since version 1.7 and removed since version 1.9. You should switch to the dynamic form of .on() which would change from this:
$('#go_btn').live('click', function () {
to this:
$(document).on('click', '#go_btn', function () {
Ideally, instead of $(document), you would pick a closer parent of #go_btn that is static (e.g. not dynamically created) as this is more efficient than using $(document), particularly if you have a number of delegated event handlers like this.
Some references for delegated event handling with .on():
jQuery .live() vs .on() method for adding a click event after loading dynamic html
Should all jquery events be bound to $(document)?
Does jQuery.on() work for elements that are added after the event handler is created?

ajax prevent double posting on mouseenter

Can someone point out what I need in my code to stop it doubling up on data when you mouseenter on the hyperlink tag. I put a flag in there isLoading but it still continues to double up. I've probably done it wrong could someone have a look through my code and see whats wrong with it - see if you can prevent it from double posting on mouseenter. Please show me you're changes - Thanks from KDM.
(function($){
$.fn.rating_display = function() {
var _this = this;
var id = $(_this).data('id');
var position = $(this).parent().position();
var left = position.left - 15;
var top = position.top + $(this).height() + 13;
var isLoading = false;
function clear_ratings() {
$('.ratings-content').html("");
}
$(document).on('click', function(e) {
var element = e.target;
/*else if($(element).closest('.rating').length){
$('.ratings-display').show();
}*/
});
// here is where I'm having trouble with double posting
$(this).on('mouseenter click', function(e) {
if(isLoading == true) return false;
$.ajax({
type:'POST',
dataType:"html",
data:{product_id:id},
url:"../../webservices/get_rating.php",
beforeSend: function() {
clear_ratings();
$('.ratings-display').show().css({'left':left + 'px', 'top':top + 'px'});
isLoading = true;
},
success: function(data) {
$('.ratings-content').append(data);
}, error:function(data, status, xhr) {
clear_ratings();
$('.ratings-content').html(data + "\r\n" + status + "\r\n" + xhr);
}
});
}).on('mouseleave', function(e) {
var target = e.relatedTarget;
if($(target).closest('.ratings-display').length) {
return false;
}else{
$('.ratings-display').hide();
clear_ratings();
isLoading = false;
}
});
$('.ratings-display').on('mouseleave',function (e) {
var target = e.relatedTarget;
if($(target).closest('.rating').length) return false;
if(!$(target).closest('.ratings-display').length) {
$('.ratings-display').hide();
clear_ratings();isLoading = false;
}
});
}
})(jQuery);
'mouseenter click' means the action is performed once at mouseenter and again if you click.
Try setting isLoading = true; before the ajax call rather than in the beforesend function. And you also want to reset isLoading = false on ajax call completion rather than on mouseleave. Depending on whether you're doing it for keyboard navigation reasons or not, you could also stop listening to the click event entirely.

Categories