Error within my jQuery plugin - javascript

I was just wondering if I could get some assistance, I have dwelled on this for hours and have a feeling I'm forgetting something basic that maybe an extra pair of eyes can help me with
(function($) {
jQuery.fn.center = function(options) {
var settings = $.extend({
hasParent: false,
leftoffset: 0,
topoffset: 0
}, options );
return this.each(function(){
var parent;
if (settings.hasParent) {
parent = $(this).parent();
} else {
parent = window;
}
$(this).css({
"position": "absolute",
"top": ((($(parent).height() - $(this).outerHeight()) / 2) + $(parent).scrollTop() + settings.topoffset + "px"),
"left": ((($(parent).width() - $(this).outerWidth()) / 2) + $(parent).scrollLeft() + settings.leftoffset + "px")
});
});
};
})(jQuery);
The above is the plugin that I have created, but am unable to see an error in, although I am only getting errors in Internet Explorer saying the following
Object doesn't support property or method 'center'
I call this plugin with the following code
$(".center").center({hasParent: true});
UPDATE:
Index File that uses the script
<script src = "http://code.jquery.com/jquery-1.11.1.min.js"></script>
<script src = "asset/shiv/dist/html5shiv.js"></script>
<script src = "asset/center.js"></script>
<script>
$(window).load(function(){
$ = jQuery.noConflict();
$("#container").css("height", $(window).height() + "px");
$("#container").css("width", $(window).width() + "px");
$(".center").center({hasParent: true});
$(".center").children().css("opacity", 0);
$(".center").css("visibility", "visible");
var LogoTop = parseInt($("#Logo").css("top"));
var LTTop = parseInt($("#LTText").css("top"));
var CSTop = parseInt($("#ComingSoonText").css("top"));
$("#Logo").css("top", LogoTop - 500);
$("#LTText").css("top", LTTop - 500);
$("#ComingSoonText").css("top", CSTop + 500);
$("#Logo").animate({
opacity: 1,
top: LogoTop
}, 1000, function(){
$("#LTText").animate({
opacity: 1,
top: LTTop
}, 750);
$("#ComingSoonText").animate({
opacity: 1,
top: CSTop
}, 750);
});
$(window).on("resize", function(){
$("#container").css("height", $(window).height() + "px");
$("#container").css("width", $(window).width() + "px");
$(".center").center({hasParent: true});
}).trigger('resize');
});
</script>

Related

javascript global variable good practice

I have a few variables pertaining to the height of elements an want to update them using $(window).on('resize'[...]), as well as calculate them when first loading the page so naturally I would rather make a function for doing that, instead of repeating the code.
Is it bad practice to make these variables global so that I can update them with a function, or is there any other way to do this?
var hSum = 0
for (var i = 0; i < content.length; i++) {
var contentH = $(content[i]).height()
hSum += contentH
}
var windowHeight = $(window).height(),
footerHeight = footer.height(),
heightDocument = windowHeight + hSum + footer.height() - 20;
This is the entirety of the script
function scrollFooter(scrollY, footerHeight) {
if (scrollY >= footerHeight) {
$('footer').css({
'bottom': '0px'
});
} else {
$('footer').css({
'bottom': '-' + footerHeight + 'px'
});
}
}
$(document).ready(function() {
var content = $('.content'),
header = $('header'),
footer = $('footer'),
headerContainer = header.find('.container'),
headerBackground = header.find('.background'),
nav = $('.navbar')
var hSum = 0
for (var i = 0; i < content.length; i++) {
var contentH = $(content[i]).height()
hSum += contentH
}
var windowHeight = $(window).height(),
footerHeight = footer.height(),
documentHeight = windowHeight + hSum + footer.height() - 20;
$('#scroll-animate, #scroll-animate-main').css({
'height': documentHeight + 'px'
})
$('header').css({
'height': windowHeight + 'px'
})
$('.wrapper-parallax').css({
'margin-top': windowHeight + 'px'
})
scrollFooter(window.scrollY, footerHeight);
setTimeout(function fadeHeaderIn() {
headerContainer.css('opacity', '1')
headerBackground.css('transform', 'scale(1.25, 1.25)')
}, 300)
$(window).on('scroll', function() {
scroll = window.scrollY
$('#scroll-animate-main').css({
'top': '-' + scroll + 'px'
});
scrollFooter(scroll, footerHeight);
nav.toggleClass('hidden', scroll < windowHeight)
})
nav.on("mouseenter", function() {
nav.removeClass('minimized')
})
nav.on("mouseleave", function() {
nav.addClass('minimized')
})
$('.navbutton').on('click', function(event) {
if ($(this).attr('href') == "#contact")
$('html, body').stop().animate({ scrollTop: documentHeight }, 300, 'swing')
else $('html, body').stop().animate({ scrollTop: $($(this).attr('href')).offset().top }, 300, 'swing')
event.preventDefault()
})
})
The best thing to do is to create a class to handle all the element functions.
for example, let's assume that you have a div or a canvas that you want to check for it's size.
function divHandler(divID){
this.div = document.getElementById(divID);
//Add all global variables here
this.boundingRect = this.div.getBoundingClientRect()
}
//After that access the variables by other functions
divHandler.prototype.displayData = function(){
console.log(this.boundingRect);
}
const d = new divHandler('someDiv');
d.displayData();
#someDiv{
min-width: 100px;
min-height: 100px;
border: 1px solid black;
}
<div id="someDiv">
</div>
Now you have a class that controls all divs by id and you can use it again and again for all other divs in the code.
Update 1:
You can also add an event listener like this
function divHandler(divID){
this.div = document.getElementById(divID);
//Add all global variables here
this.boundingRect = this.div.getBoundingClientRect()
}
divHandler.prototype.listen = function (event, cb, ...args){
this.div.addEventListener(event,cb.bind(this, ...args));
}
const d = new divHandler('someDiv');
d.listen('click', function(e){
console.log(e.type);
this.div.style.backgroundColor = "blue"
});
#someDiv{
min-width: 100px;
min-height: 100px;
border: 1px solid black;
}
<div id="someDiv"></div>

Issue with jQuery-based carousel and window resize

I have a weird bug in my code that is causing my carousel to act funny if the window is resized.
I haven't been able to pin-point what may be causing the issue, but if you run the code and then resize the window, the carousel will start to move back and forth rapidly, avoiding the 10-second timer that I have placed on it.
Here is a link to my example fiddle: https://jsfiddle.net/zeropsi/ufvLn25b/
Any thoughts?
The trouble is when window is being resized, the window.resize gets triggered a number of times and because of that carousel keeps sliding rapidly. I searched for 'jquery window resize trigger once complete' and found help. This is how I modified your code from the fiddle.
<script>
$(document).ready(function() {
$(document).on("click", ".carousel-indicators li", function() {
$(".carousel-indicators li").removeClass("active");
var a = $(this).data("slide");
$(this).addClass("active");
$("div#billboards").animate({
"left": (a * -100) + "%"
});
$(".billboard").removeClass("active");
$(".billboard[data-billboard='" + a + "']").addClass("active");
return false;
});
// var resizeTimer;
//
// $(window).on("resize", function() {
// console.log("window resized");
//
// clearTimeout(resizeTimer);
// resizeTimer = setTimeout(function() {
// // run code here, resizing has stopped
// BillboardCarousel.init();
// },10000);
//
// });
var id;
$(window).on("resize", function() {
clearTimeout(id);
id = setTimeout(doneResizing, 500);
});
function doneResizing(){
BillboardCarousel.init();
}
if ($("section#carousel").length === 1) {
BillboardCarousel.init();
}
});
var BillboardCarousel = {
init: function() {
BillboardCarousel.resize();
},
imagesLoaded: function() {
var imagesLoaded = 0;
$(".billboard").each(function() {
var image = new Image();
image.src = $(this).data("image");
image.onload = function() {
imagesLoaded++;
if (imagesLoaded === $(".billboard").length) {
BillboardCarousel.startCarousel();
}
};
});
},
startCarousel: function() {
var interval = parseInt($("div#billboards").data('interval'));
window.setInterval(function() {
BillboardCarousel.timer();
}, 10000);
},
resize: function() {
var a = $(".billboard").length;
var b = $(window).width();
$(".billboard").css({
"width": b + "px",
"float": "left",
"display": "inline-block"
});
$("div#billboards").css({
"width": a * 100 + "%",
"left": "0%"
});
$("div#billboards").attr("data-interval", 10000);
BillboardCarousel.imagesLoaded();
},
timer: function() {
var a = $(".billboard.active").data("billboard");
a++;
if (a >= $(".billboard").length) {
a = 0;
}
$(".billboard").removeClass("active");
$(".carousel-indicators li").removeClass("active");
$(".billboard[data-billboard='" + a + "']").addClass("active");
$(".carousel-indicators li[data-slide='" + a + "']").addClass("active");
$("div#billboards").animate({ "left": (a * -100) + "%" });
}
};
</script>
These are a few helpful links -
JQuery: How to call RESIZE event only once it's FINISHED resizing?
http://jsfiddle.net/Zevan/c9UE5/1/
https://css-tricks.com/snippets/jquery/done-resizing-event/

Centering Special Javascript Popup, How?

I have this javascript code, lib.js. It manages my every java popup in my site. How ever it is not set to be appear absolutely centered in page, I have tried several css codes for its div. But it did not work. I also tried the famous /2 code but it didnt work or I might have added it to wrong place.
Below is my lib.js:
var currentTime = new Date();
var topP = 0;
$(document, window).keypress(function(e){
if (e.keyCode == 27){
$(".yekbox").fadeOut();
$("#yekbox_overlay").hide();
}
});
$(document).ready(function() {
$(".showme").unbind().hover(
function(e) {
$(".tooltip").remove();
this.t = $(this).next(".description").html();
$(this).append( '<div class="tooltip">' + this.t + '</div>' );
},
function() {
//this.title = this.t;
$(".tooltip").remove();
}
).mousemove(
function(e) {
$(".tooltip").css({
"top" : e.pageY + 20,
"left" : e.pageX + 20
});
}
);
topP = $(this).scrollTop();
//$(".yekbox").css("top", $(window).height()-250 + "px");
//$(".yekbox").css("left", $(window).width()-(440*2) + "px");
$("#yekbox_overlay").css("height", $(window).height());
$(window, document).resize(function(){
topP = $(this).scrollTop();
$(".yekbox").css("marginTop", topP-250 + "px");
if ($(window).width() > 900 ) $(".yekbox").css("left", $(window).width()-(440*2) + "px");
$(".yekbox").css("marginLeft", "auto");
$(".yekbox").css("marginRight", "auto");
$("#yekbox_overlay").css("height", $(window).height());
});
$(window).scroll(function () {
topP = $(this).scrollTop();
$(".yekbox:visible").css("marginTop", topP-250 + "px");
$("#yekbox_overlay:visible").css("height", $(window).height());
});
$(window).bind("scroll",function () {
topP = $(this).scrollTop();
$(".yekbox:visible").css("marginTop", topP-250 + "px");
$("#yekbox_overlay:visible").css("height", $(window).height());
});
$("#yekbox_overlay").click(function(){
$(".yekbox").fadeOut();
$(this).hide();
return false;
});
The JS and HTML code above doesn't help in anything.
In general, if you want a block to be centered to the parent, it should have
A fixed width
margin: auto
If you want a block absolutely centered (position absolute or fixed)
$('#mypopup').css('left', ($(window).width() - $('#mypopup').width()) / 2)

Drag and Drop -JQuery

Im creating myself a drag functions just for my personal use so I can drag elements around. I'm having a problem. At the moment trying to make the drag so one you pick up the element you can drag it but once you drop it, it goes back to the original position. This is not working as you can see here. When I let go of #drag2 or #drag3 then it goes to the position of #drag1.
My Function:
function drag(el) {
var position = $(el).position();
var ptop = position.top;
var pleft = position.left;
var down = false;
$(el).mousedown(function(event) {
down = true;
$(this).css({
cursor: 'crosshair',
});
$(this).mousemove(function(event) {
if (down == true) {
$(this).css({
cursor: 'crosshair',
});
var w = $(this).width();
var h = $(this).height();
var left3 = (w / 2) + 7;
var top3 = (h / 2) + 7;
$(this).css({
cursor: 'crosshair',
left: (event.clientX) + (3 * 3) - left3,
top: (event.clientY) + (3 * 3) - top3
});
}
}).mouseup(function() {
down = false;
$(this).css({
cursor: 'default',
});
$(this).animate({
top: ptop,
left: pleft
}, 300);
});
});
}
I have to get the old position:
var position = $(el).position();
var ptop = position.top;
var pleft = position.left;
So should it not get the position of all of them and bring them self back to where they were? Any help will be appreciated.
EDIT: I DO NOT WANT TO USE ANY PLUGIN OR JQUERY UI, THANKS ANYWAYS
The solution is very simple
See this fiddle: http://jsfiddle.net/BggPn/4/
you define 1 var for left and 1 for top. All 3 the elements use the same variables. If you loop through the elements then you make a new scope where each element has it's own vars.
Working code:
$(document).ready(function() {
drag('#drag, #drag2, #drag3')
});
function drag(el) {
$(el).each(function(){
var position = $(this).position();
var ptop = position.top;
var pleft = position.left;
var down = false;
$(this).mousedown(function(event) {
down = true;
$(this).css({
cursor: 'crosshair',
});
$(this).mousemove(function(event) {
if (down == true) {
$(this).css({
cursor: 'crosshair',
});
var w = $(this).width();
var h = $(this).height();
var left3 = (w / 2) + 7;
var top3 = (h / 2) + 7;
$(this).css({
cursor: 'crosshair',
left: (event.clientX) + (3 * 3) - left3,
top: (event.clientY) + (3 * 3) - top3
});
}
}).mouseup(function() {
down = false;
$(this).css({
cursor: 'default',
});
$(this).animate({
top: ptop,
left: pleft
}, 300);
});
});
});
}
Make it a plugin:
$.fn.drag = function drag(){
return this.each(function(){
var position = $(this).position();
var ptop = position.top;
var pleft = position.left;
var down = false;
$(this).mousedown(function(event) {
down = true;
$(this).css({
cursor: 'crosshair',
});
$(this).mousemove(function(event) {
if (down == true) {
$(this).css({
cursor: 'crosshair',
});
var w = $(this).width();
var h = $(this).height();
var left3 = (w / 2) + 7;
var top3 = (h / 2) + 7;
$(this).css({
cursor: 'crosshair',
left: (event.clientX) + (3 * 3) - left3,
top: (event.clientY) + (3 * 3) - top3
});
}
}).mouseup(function() {
down = false;
$(this).css({
cursor: 'default',
});
$(this).animate({
top: ptop,
left: pleft
}, 300);
});
});
});
}
Now you can call it by:
$("#drag1, #drag2").drag();
2 thoughts:
1.) Why don't you use jQuery UI (draggable)?
2.) The idea of giving a selector in stead of an element is wrong, a selector can lead to multiple elements, and that's the first reason why it's failing. If you start with
function drag(selector) {
$(selector).each(function() {
var el = $(this);
//rest of code
}
}
it would be better. But I think you'll run into a few other problems eventually
The problem is whenever you're sending in the list of selectors '#drag, #drag2. #drag3' and your position variable only cares about the first one (try changing the order and you'll see they snap to the first in the list). If you want to go about it this way then you'll want to perform an each iteration over them to get the right values.
get the current position of div after drag and set via this
.mouseup(function() {
var position = $(this).position();
down = false;
$(this).css({
cursor: 'default',
});
$(this).animate({
top: position.top,
left: position.left
}, 300);
DEMO
why don't you use drag and drop plugin. see this article
http://viralpatel.net/blogs/2009/05/implement-drag-and-drop-example-jquery-javascript-html.html
or this one
http://plugins.jquery.com/project/dragndrop

jQuery each width problem

I have the following function set to run on a hover over an image:
function() {
$('.slides .slide h3').each(function(i){
var owidth = $(this).width()
$(this).animate({"right":730 - owidth - 16}, 500);
});
}
You can view the page here. Over the image and click the next icon on the lower right of the image. For some reason, the function is calculating the first h3's width correctly, but then it thinks all other h3s have a width of 0. Can anyone offer a solution?
function() {
var owidth = 0;
$('.slides .slide h3').each(function(i){
owidth = $(this).width();
$(this).animate({"right":(730 - owidth - 16) + 'px'}, 500);
});
}
A better way:
function() {
$('.slides .slide h3').each(function(i){
$(this).stop().animate({
"right": (714 - $(this).width()) + 'px'
}, 500);
});
}

Categories