Плавный scroll элементов на javascript

javascript, 04.12.2009 Пятница, 20:00
Теги: Анимация, javascript, полезное, scroll
     Я давно уж ничего не писал, да и мыслей, достойных публикации не возникало. Но забрасывать блог не хотелось, поэтому я решил написать о ещё одной небольшой проблемке в javascript. Сегодня я покажу, как сделать плавный анимированный скрол любого элемента.
     Анимацию я сделал с помощью своей любимой анимационной функции, которую использую практически для всех операций подобного рода. На этот раз все функции и переменные убраны в объект scroll - просто для того чтобы создать закрытый неймспейс и случайно не пересечься с другими переменными.
     Собственно о скролле: скролл бывает разный. Есть скролл различных дом элементов, например дивов с параметром overflow:scroll или текстовых полей. Он реализуется с помощью присвоения значений scrollTop и scrollLeft. Но есть и другой вид скролла. Это скролл окна браузера - объекта window. Он осуществляется специальным методом scrollTo().
     Текущее положени скролла как у окна браузера так и у различных элементов получается достаточно легко, нужно только учесть, что в режиме соответствия стандартам браузер выдает информацию о скролле окна браузера только при обращении к documentElement а не к document.body. На этом сложности заканчиваются.
     От слов к делу, вот функция, осуществляющая скролл как в элементах так и в окне браузера.
Code
<script type='text/javascript'>
Scroll = {
  sL:function(o){return o!=window?o.scrollLeft:document.body.scrollLeft||document.documentElement.scrollLeft},
  sT:function(o){return o!=window?o.scrollTop:document.body.scrollTop||document.documentElement.scrollTop},  
  anim:function(p){function d(p){return Math.pow(p,3)};if(p<0.5){return d(2*p)/2;}else{return (2-d(2*(1-p)))/2;}}, // рассчет анимации
  animator:[], /* массив с анимируемыми объектами */
  anielems:0, /* счетчик анимируемых объектов */
  to: function(obj,values,time,callback){
  // перебираем параметры и значения
  for(key in values){anima(key,values[key])}
  function anima(param,to){
  // проверяем и останавливаем предыдущие анимации
  for(key in Scroll.animator){if(Scroll.animator[key].o==obj&&Scroll.animator[key].p==param){clearInterval(Scroll.animator[key].timer)}}
  var aID=Scroll.anielems,
  result,
  now,
  progress,
  w=obj==window?1:0,
  param=param=='x'?1:0,
  from=param?Scroll.sL(obj):Scroll.sT(obj);
  Scroll.animator[aID] = {
  start: new Date().getTime(),
  timer: setInterval(function(){
  now=(new Date().getTime())-Scroll.animator[aID].start;
  progress=now/time;
  result=(to-from)*Scroll.anim(progress)+from;
  if(param){
  if(w){window.scrollTo(result,Scroll.sT(obj))}
  else{obj.scrollLeft=result}
  }else{
  if(w){window.scrollTo(Scroll.sL(obj),result)}
  else{obj.scrollTop=result}
  }
  if(progress>=1){
  clearInterval(Scroll.animator[aID].timer);
  if(param){
  if(w){window.scrollTo(to,Scroll.sT(obj))}
  else{obj.scrollLeft=to}
  }else{
  if(w){window.scrollTo(Scroll.sL(obj),to)}
  else{obj.scrollTop=to}
  }
  if(callback){callback()}
  }
  },10)
  }
  Scroll.anielems++;
  }
  }
  };
</script>
     Функция проверена во всех версиях осла ну и соответственно во всех остальных популярных браузерах. Ошибок нет. выполняется ровно. Вызывается вот так:
Code
<script type='text/javascript'>
Scroll.to(window,{'x':500,'y':300},400);
// прокрутит окно браузера на заданное количество
// пикселей по горизонтали и вертикали за 400 миллисекунд
Scroll.to(mydiv,{'y':200},1000,function(){ alert('') });
// прокрутит по вертикали див блок за 1000мс и выдаст алерт
// ну и так далее
</script>
     Пример работы именно этой функции я приводить не буду, но так как аналогичный способ прокрутки используется на моем сайте, я просто приведу в пример пару ссылок: прокрутить страницу наверх (скорость 300мс) и прокрутить страницу на 600px (скорость 500мс, alert по завершении).
     + за пост в карму на форуме =)

Жми на пятую!
29, 8, 9515
№8
А зачем ты все в объект выделил? Почему не пользоваться обычными переменными?
Ответ: Чтобы глобальную область видимости не занимать.
№7
[sayto]Иван0[/sayto], аааа, да, спасибо.
№6
[sayto]Иван0[/sayto], что скачет? O_o
№5
Интересно на форуме скачет
№4
[sayto]Aleko[/sayto], +1 :)
№3
Прикольный скрипт, спасибки!)
№2
Спасибо, отличное решение
№1
Хм... утащил себе
    © Блог StudioAD.ru 2024 год нашей эры. Не все права защищены... Копирование любой информации и материалов с обратной ссылкой приветствуется! Хостинг от uCoz.

    Если вам пришлись по душе материалы моего блога - подпишитесь на RSS дабы получать обновления незамедлительно! Я рад что вы читаете и комментируете мои экзерсисы, приятного времяпрепровождения.