I've made an attempt here based on some things I have gleaned, but this is just plain removing it altogether; the title doesn't return back at <= 768px
<script>
if( $(window).width() > 767) {
$('[title]').each( function() {
var $this = $(this);
$this.data('title',$this.attr('title'));
$this.removeAttr('title');
});
}
</script>
See http://jsfiddle.net/2nHxV/
if ($(window).width() > 767) {
$('[title]').each( function() {
var $this = $(this);
$this.data('title',$this.attr('title'));
$this.removeAttr('title');
});
} else {
// as in above `title` attribute removed and `data-title` added, so now you've
// to loop with data-title
$('[data-title]').each( function() {
var $this = $(this);
$this.data('title',$this.data('title'));
$this.removeAttr('data-title');
});
}
So put it back?
var $titles = [];
if( $(window).width()> 767) {
$('[title]').each( function() {
var $this = $(this);
$this.data('title',$this.attr('title'));
$this.removeAttr('title');
$titles.push($this);
});
} else {
$.each($titles, function(index, $this) {
$this.attr('title',$this.data('title'));
});
}
Working demo: http://jsfiddle.net/z3rr9d04/
You also might want to put this logic inside a $(window).on('resize', ...); handler since it'll only be executed once on page load as it stands currently.
Related
I am trying to add class or remove class on getting element top by using This DEMO . Here is the code as well:
$(document).ready(function () {
var sec1_offset = $("#sec1").offset();
var sec2_offset = $("#sec2").offset();
var sec3_offset = $("#sec3").offset();
var sec4_offset = $("#sec4").offset();
var sec5_offset = $("#sec5").offset();
var sec6_offset = $("#sec6").offset();
var sec7_offset = $("#sec7").offset();
$("section").scroll(function () {
if (sec4_offset.top < 100) {
alert("You Are in Sec 4");
}
});
});
I also change the $("section").scroll(function () { to $(body).scroll(function () { and $(document).scroll(function () { but it didn't work!
Can you please let me know what I am doing wrong? Thanks
You can listen to the scroll event of the window object, scroll event like the resize event is fired so many times, for efficiency you can throttle the handler, ie the handler is executed after a specified timeout.
$(document).ready(function () {
var $sec = $("section"),
handle = null;
var $w = $(window).scroll(function () {
// clear the timeout handle
clearTimeout(handle);
// throttling the event handler
handle = setTimeout(function() {
var top = $w.scrollTop();
// filtering the first matched element
var $f = $sec.filter(function() {
return $(this).offset().top + $(this).height() >= top;
}).first().addClass('active');
$sec.not($f).removeClass('active');
}, 50);
}).scroll();
});
http://jsfiddle.net/UTCER/
edit: If you want to add a class to another element, the most efficient way is using the index method:
// Cache the object outside the `scroll` handler
var $items = $('#menu li');
// within the `setTimeout` context:
var $f = $sec.filter(function() {
return $(this).offset().top + $(this).height() >= top;
}).first();
$items.removeClass('active').eq( $sec.index($f) ).addClass('active');
use $(window).scroll for the scroll event listener
also you want to check sec4_offset.top against window.scrollY
JS
$(document).ready(function () {
var sec1_offset = $("#sec1").offset();
var sec2_offset = $("#sec2").offset();
var sec3_offset = $("#sec3").offset();
var sec4_offset = $("#sec4").offset();
var sec5_offset = $("#sec5").offset();
var sec6_offset = $("#sec6").offset();
var sec7_offset = $("#sec7").offset();
$(window).scroll(function () {
if (window.scrollY >= sec4_offset.top) {
alert("You Are in Sec 4");
}
});
});
JSFiddle Demo
Use $(window).scroll()
Here's what jQuery documentation says about scroll event
The scroll event is sent to an element when the user scrolls to a different place in the element. It applies to window objects, but also to scrollable frames and elements with the overflow CSS property set to scroll (or auto when the element's explicit height or width is less than the height or width of its contents).
I know this answer has already been answered, but I'd like to provide an alternative answer on JSFiddle that might accomplish what you're looking for to a more dynamic extent. I would not ask to be voted as the answer, but simply noted as a reference for an alternative approach to this problem
http://jsfiddle.net/mLfAq/5/
$(document).ready(function () {
var offsets = [];
$('[id^="#sec"]').each(function() {
offsets.push([$(this).attr('id'), $(this).offset().top + $(this).height()]);
});
$(window).scroll(function () {
for(var i = 0; i < offsets.length; i++) {
if(offsets[i][1] > $(window).scrollTop()) {
console.log('You are in ' + offsets[i][0]);
return;
}
}
});
});
I have two click-events, that are nearly similar, but not quite. I am wondering how to refactor them best:
$('.remove_fields.dynamic').live('click', function(e) {
var $this = $(this);
var after_removal_trigger_node = $this.closest(".nested-fields").parent();
trigger_removal_callback($this);
e.preventDefault();
$this.closest(".nested-fields").remove();
trigger_after_removal_callback(after_removal_trigger_node);
});
$('.remove_fields.existing').live('click', function(e) {
var $this = $(this);
var after_removal_trigger_node = $this.closest(".nested-fields").parent();
trigger_removal_callback($this);
e.preventDefault();
$this.prev("input[type=hidden]").val("1");
$this.closest(".nested-fields").hide();
trigger_after_removal_callback(after_removal_trigger_node);
});
As you can tell there is a fair bit of overlap. I am wondering what the best/nicest way would be to refactor this code.
Do a class check in the .remove_fields click function.
$('.remove_fields').click(function(e) {
var $this = $(this);
var after_removal_trigger_node = $this.closest(".nested-fields").parent();
trigger_removal_callback($this);
e.preventDefault();
if($this.hasClass("dynamic") {
$this.closest(".nested-fields").remove();
} else if($this.hasClass("existing")) {
$this.prev("input[type=hidden]").val("1");
$this.closest(".nested-fields").hide();
}
trigger_after_removal_callback(after_removal_trigger_node);
});
Combine the selectors into $('.remove_fields.dynamic, .remove_fields.existing').
Then, test if $this has class existing. If so, run $this.prev("input[type=hidden]").val("1");.
Done.
taking cleaning a bit more:
$('.remove_fields').click(function(e) {
e.preventDefault();
var $this = $(this);
var $nestedFields = $this.closest(".nested-fields");
trigger_removal_callback($this);
if($this.hasClass("dynamic") {
$nestedFields.remove();
} else if($this.hasClass("existing")) {
$this.prev("input[type=hidden]").val("1");
$nestedFields.hide();
}
trigger_after_removal_callback($nestedFields.parent());
});
I'm trying to add some functionality to be able to edit comments inline. So far it's pretty close, but I'm experiencing issues trying to trigger a second event. It works the first time, but after that, fails.
$(function() {
var $editBtn = $('.js-edit-comment-btn');
var clicked = false;
$editBtn.on('click', $editBtn, function() {
clicked = true;
var $that = $(this);
var $form = $that.closest('.js-edit-comment');
var $commentTextBody = $that.closest('div').find('.js-comment-body');
var commentText = $commentTextBody.text();
var $editableText = $('<textarea />');
if ($that.text() === 'Save Edits') {
$that.text('Saving...').attr('disabled', true);
} else {
$that.text('Save Edits').attr('alt', 'Save your edits');
}
// Replace div with textarea, and populate it with the comment text
var makeDivTextarea = function($editableText, commentText, $commentTextBody) {
$editableText.val(commentText);
$commentTextBody.replaceWith($editableText);
$editableText.addClass('gray_textarea js-edited-comment').width('100%').css('padding', '4px').focus();
};
makeDivTextarea($editableText, commentText, $commentTextBody);
var saveEdits = function($that, $editableText) {
$that.on('click', $that, function() {
if (clicked) {
var comment = $that.closest('div').find('.js-edited-comment').val();
$editableText.wrap('<div class="js-comment-body" />').replaceWith(comment);
$that.text('Edit').attr('alt', 'Edit Your Comment').attr('disabled', false);
$('#output').append('saved');
clicked = false;
return false;
}
});
};
saveEdits($that, $editableText);
return false;
});
});
jsfiddle demo here
Hiya demo for your working solution: http://jsfiddle.net/8P6uz/
clicked=true was the issue :)) I have rectified another small thing. i.e. $('#output') is set to empty before appending another saved hence text **saved** will only appear once.
small note: If I may suggest use Id of the button or if there are many edit buttons try using this which you already i reckon; I will see if I can write this more cleaner but that will be sometime latter-ish but this should fix your issue. :) enjoy!
Jquery Code
$(function() {
var $editBtn = $('.js-edit-comment-btn');
var clicked = false;
$editBtn.on('click', $editBtn, function() {
clicked = true;
var $that = $(this);
var $form = $that.closest('.js-edit-comment');
var $commentTextBody = $that.closest('div').find('.js-comment-body');
var commentText = $commentTextBody.text();
var $editableText = $('<textarea />');
if ($that.text() === 'Save Edits') {
$that.text('Saving...').attr('disabled', true);
} else {
$that.text('Save Edits').attr('alt', 'Save your edits');
}
// Replace div with textarea, and populate it with the comment text
var makeDivTextarea = function($editableText, commentText, $commentTextBody) {
$editableText.val(commentText);
$commentTextBody.replaceWith($editableText);
$editableText.addClass('gray_textarea js-edited-comment').width('100%').css('padding', '4px').focus();
};
makeDivTextarea($editableText, commentText, $commentTextBody);
var saveEdits = function($that, $editableText) {
$that.on('click', $that, function() {
if (clicked) {
var comment = $that.closest('div').find('.js-edited-comment').val();
$editableText.wrap('<div class="js-comment-body" />').replaceWith(comment);
$that.text('Edit').attr('alt', 'Edit Your Comment').attr('disabled', false);
$('#output').text("");
$('#output').append('saved');
clicked = true;
return false;
}
});
};
saveEdits($that, $editableText);
return false;
});
});
I am using the ajaxify.js plugin https://github.com/browserstate/ajaxify to load content dynamically.
I have a number of click functions that I bind on document ready, but have to additionally put those functions inside of my ajax load function to re-bind the click events to the newly added content. I had tried using a single set of live functions previously but they didn't work.
Anyway I have the following code twice, once inside of a document.ready(function(){ }) and once again inside of ajaxify.js after the content loads.
I know it's superfluous, but I'm not sure of how to go about writing the functions just once so I can "include" them elsewhere. How can I optimize these functions so I can consolidate them and use them over again in an efficient manner?
Thank you!
var $filterclear = $('.filters .filter-clear'),
filtercount = $filterclear.length,
$searchedfor = $('.searched-for'),
is_search = $searchedfor.length;
$filterclear.bind('click', function(){
var $me = $(this);
if(filtercount == 3) {
$('.clear-all.filter-clear').addClass('filter-out').fadeOut('fast');
$(this).addClass('filter-out').fadeOut('fast');
} else {
$(this).addClass('filter-out').fadeOut('fast');
}
if($me.hasClass('clear-all') || filtercount == 1) {
$filterclear.addClass('filter-out').fadeOut('fast');
if(is_search !== 0) {
$('.filters').fadeOut();
}
}
});
$('.tag.remove-term').bind('click', function(){
var $me = $(this),
mytext = $me.text(),
$myfilter = $('.filters .filter-clear:contains("'+ mytext +'")');
if(filtercount == 3) {
$('.clear-all.filter-clear').addClass('filter-out').fadeOut('fast');
$myfilter.addClass('filter-out').fadeOut('fast');
} else {
$myfilter.addClass('filter-out').fadeOut('fast');
}
});
$searchedfor.find('.filter-clear').bind('click',function(){
$searchedfor.fadeOut();
});
Defining a new function should work (I didn't test it):
var $filterclear = $('.filters .filter-clear'),
filtercount = $filterclear.length,
$searchedfor = $('.searched-for'),
is_search = $searchedfor.length;
var doSomething($myfilter) {
if(filtercount == 3) {
$('.clear-all.filter-clear').addClass('filter-out').fadeOut('fast');
}
$myfilter.addClass('filter-out').fadeOut('fast');
};
$filterclear.bind('click', function() {
var $me = $(this);
doSomething($me);
if($me.hasClass('clear-all') || filtercount == 1) {
$filterclear.addClass('filter-out').fadeOut('fast');
if(is_search !== 0) {
$('.filters').fadeOut();
}
}
});
$('.tag.remove-term').bind('click', function(){
var $me = $(this),
mytext = $me.text(),
$myfilter = $('.filters .filter-clear:contains("'+ mytext +'")');
doSomething($me);
});
$searchedfor.find('.filter-clear').bind('click',function(){
$searchedfor.fadeOut();
});
I try to do this image effects: http://coverdesign.ro/teste/lore/ but sometimes when the mouse move from one object to another it lose the hover state;
I use this js script:
$(function () {
$('div.fade').hover(function() {
fade = $('> div', this);
nume = $(this).attr('id');
$("."+nume).addClass("mselect");
if (fade.is(':animated')) {
fade.stop().fadeTo(250, 1);
} else {
fade.fadeIn(1000);
}
}, function () {
/* var fade = $('> div', this);
var nume = $(this).attr('id');*/
$("."+nume).removeClass("mselect");
if (fade.is(':animated')) {
fade.stop().fadeTo(250, 0);
} else {
fade.fadeOut(500);
}
});
$('#menu a').hover(function() {
var nume = $(this).attr('class');
var fade = $('#'+nume+' > div');
//$("."+nume).addClass("mselect");
if (fade.is(':animated')) {
fade.stop().fadeTo(250, 1);
} else {
fade.fadeIn(2000);
}
}, function () {
var nume = $(this).attr('class');
var fade = $('#'+nume+' > div');
if (fade.is(':animated')) {
fade.stop().fadeTo(2000, 0);
} else {
fade.fadeOut(2000);
}
});
});
What actually happens is, sometimes when the mouse is moved from the cat to the phone, the hover does not get activated. If you play around with the page you will realise that the color change of the cat and the phone, sometimes does not happen due to hover state being lost.
I guess this line of code
$('div.fade').hover(function() {
is causing a problem in identifying the proper div. You could try uniquely identifying each menu item/image and handle it accordingly.