gibney.org
:
Technology
:
Javascript
:
Includes
:
Overflow Scroller
(Entry Nr. 374, by user 70 |
edit
)
/* - Doesn't work in Safari (at least the Example in /Technology/Javascript/Includes looks crappy, might also be a style rendering fault which occurs in this special setup since in the M1D1 menu Safari seems to deliver correctly). - Uses document.body.scrollLeft / document.body.scrollTop. Rumors say, this might not work when certain doctypes are set and the browser is IE6 (we didn't test this yet). */ ge_require_once("http://javascript.gibney.org/2d.js"); function OverflowScroller(InnerId) { this.ScrollStart=function() { this.Brake=1; if (this.Scrolling) return; var me=this; this.Scrolling = window.setInterval(function(){me.Scroll()},20); } this.Scroll=function() { if (ge_2d.getX(this.Inner)+this.Speed>ge_2d.getX(this.Outer)) // avoid MenuBar to scroll right further than necessary { this.Inner.style.left=0; } else if (this.Outer.offsetWidth+ge_2d.getX(this.Outer)-(ge_2d.getX(this.Inner)+this.Speed)>this.Inner.offsetWidth) // don't scroll left further than necessary { this.Inner.style.left = this.Outer.offsetWidth-this.Inner.offsetWidth; window.clearInterval(this.Scrolling); this.Scrolling=false; this.Speed=0; } else { this.Inner.style.left=ge_2d.getX(this.Inner)-ge_2d.getX(this.Outer)+this.Speed; this.Speed/=this.Brake; if (this.Speed<0.5&&this.Speed>-0.5) { window.clearInterval(this.Scrolling); this.Scrolling=false; this.Speed=0; } } } this.ScrollStop=function() { this.Brake=1.3; } this.handleMouseMove=function(e) { if (this.Outer.offsetWidth>this.Inner.offsetWidth) return; // Scrolling unnecessary because Inner is narrower than Outer? if (!e) var e = window.event; this.Outer.X = ge_2d.getX(this.Outer); this.Outer.Y = ge_2d.getY(this.Outer); var MouseX = this.isDOM ? e.clientX-this.Outer.X : event.clientX-this.Outer.X; var MouseY = this.isDOM ? e.clientY-this.Outer.Y : event.clientY-this.Outer.Y; MouseX+=document.body.scrollLeft; //compensate for document scroll position MouseY+=document.body.scrollTop; if (MouseX<this.SenseArea) // Cursor is in the left SenseArea { this.Speed=Math.pow(this.MaxSpeed-MouseX/this.SenseArea*this.MaxSpeed,2)/this.MaxSpeed; this.ScrollStart(); } else if (MouseX>this.Outer.offsetWidth-this.SenseArea) // Cursor is in the right SenseArea { this.Speed=-(Math.pow(this.MaxSpeed-(this.Outer.offsetWidth-MouseX)/this.SenseArea*this.MaxSpeed,2)/this.MaxSpeed); this.ScrollStart(); } else { this.ScrollStop(); } return false; } this.handleMouseOut=function(e) { if (!e) var e = window.event; this.Outer.X = ge_2d.getX(this.Outer); this.Outer.Y = ge_2d.getY(this.Outer); var MouseX = this.isDOM ? e.clientX-this.Outer.X: event.clientX-this.Outer.X; var MouseY = this.isDOM ? e.clientY-this.Outer.Y: event.clientY-this.Outer.Y; MouseX+=document.body.scrollLeft; //compensate for document scroll position MouseY+=document.body.scrollTop; if (MouseX<0||MouseX>=this.Outer.offsetWidth||MouseY<0||MouseY>=this.Outer.offsetHeight) // extra test necessary because the event is also triggered { // when the mouse only left the inner element. this.ScrollStop(); return false; } } this.handleWindowResize=function() { this.Inner.style.left=0; } this.start=function() { this.Inner = document.getElementById(InnerId); this.Outer = this.Inner.parentNode; this.SenseArea=70; // width of the area at the borders where scrolling is triggered and accelerated the closer it gets to the border this.MaxSpeed=30; // maximum scrolling speed at border cursor position this.Speed=0; this.Scrolling=false; this.Brake=1; this.isDOM=document.getElementById && !document.all; var me=this; this.Outer.onmousemove=function(e){me.handleMouseMove(e)}; this.Outer.onmouseout=function(e){me.handleMouseOut(e)}; window.onresize=function(){me.handleWindowResize()}; // may cause problems with multiple object instances or other window resize handlers set up previously... } // this.start(); // if (ge_included_left2load<1) main(); // else setTimeout("startMain()",250); ge_require_safestart(this); }
Create a new entry at this position