Javascript.RU

Создать новую тему Ответ
 
Опции темы Искать в теме
  #1 (permalink)  
Старый 22.03.2016, 00:57
Новичок на форуме
Отправить личное сообщение для Meshock Посмотреть профиль Найти все сообщения от Meshock
 
Регистрация: 21.03.2016
Сообщений: 4

Два слайдера. Не заканчивается анимация одного, при запуске второго
Здравствуйте.
Я, можно сказать, новичок и задался вопросом - сделать несколько одинаковых простых слайдеров на одной странице. C помощью jQuery могу сделать это быстро, но вот хочу сделать на чистом JavaScript и заодно подтянуть ООП и тут проблема. При запуске одного слайдера, а затем второго, анимация первого останавливается, я так понимаю из-за глобальных переменных?
<div class="portfolio">
          <div class="case__container" id="case1">
            <div class="slider-wrap">
              <div class="slider">
                <div style="background-color: #678" class="slide slide-first">text</div>
                <div style="background-color: #f5d" class="slide">text2</div>
                <div style="background-color: #8a2" class="slide">text3</div>
                <div style="background-color: #149" class="slide">text4</div>
              </div>
            </div>
            <div class="arrow arrow-left" onclick="Slider.left('case1')"></div>
            <div class="arrow arrow-right active" onclick="Slider.right('case1')"></div>
          </div>
          <div class="case__container" id="case2">
            <div class="slider-wrap">
              <div class="slider">
                <div style="background-color: #2f8" class="slide slide-first">text</div>
                <div style="background-color: #faa" class="slide">text2</div>
                <div style="background-color: #3ff" class="slide">text3</div>
                <div style="background-color: #993" class="slide">text4</div>
              </div>
            </div>
            <div class="arrow arrow-left" onclick="Slider.left('case2')"></div>
            <div class="arrow arrow-right active" onclick="Slider.right('case2')"></div>
          </div>
        </div>


window.requestAnimFrame = (function(){
  return  window.requestAnimationFrame       ||
          window.webkitRequestAnimationFrame ||
          window.mozRequestAnimationFrame    ||
          function( callback ){
            window.setTimeout(callback, 1000 / 60);
          };
})();

var Slider = (function(){
  var width = 1100;
  var count;
  var slider;
  var wrap;
  var position;
  var tPosition;
  var startTime = undefined;

  return {
    init : function(elem) {

      slider = document.querySelector('#'+elem);
      wrap = slider.querySelector('.slider');
      position = +wrap.style.marginLeft.substr(0,wrap.style.marginLeft.length-2) || 0;
      count = slider.querySelectorAll('div.slide').length;
    
    },

    
    left : function(elem) {

      Slider.init(elem);
      tPosition = position + width;
      (position < 0) ? Slider.animateLeft(tPosition,elem) : elem.style.marginLeft = position + 'px';
    
    },

    
    right : function(elem) {

      Slider.init(elem);
      tPosition = position - width;
      (position > -(count-1)*width) ? Slider.animateRight(tPosition,elem) : elem.style.marginLeft = position + 'px';
   
    },
  

    animateLeft : function (){
      
      if ( startTime == undefined ){ 
        startTime = new Date().getTime();
      };
      
      var time = new Date().getTime();        
      var passedPart =  ((time - startTime) || 1) / 500;

      if (passedPart < 1) {
          wrap.style.marginLeft = position + (width * passedPart) + 'px';
          requestAnimFrame(Slider.animateLeft,wrap);
      }else{
          startTime = undefined;
          wrap.style.marginLeft = tPosition + 'px';
      };
    },


    animateRight : function (){
      
      if ( startTime == undefined ){ 
        startTime = new Date().getTime(); 
      };
      
      var time = new Date().getTime();        
      var passedPart =  ((time - startTime) || 1) / 500;

      if (passedPart < 1) {
          wrap.style.marginLeft = position - (width * passedPart) + 'px';
          requestAnimFrame(Slider.animateRight,wrap);
      }else{
          startTime = undefined;
          wrap.style.marginLeft = tPosition + 'px';
      };
    },
  };
})();


Подтолкните дурака в правильном направлении
извините за говнокод неаккуратный код

Последний раз редактировалось Meshock, 22.03.2016 в 10:29. Причина: Поправил немного вид
Ответить с цитированием
  #2 (permalink)  
Старый 22.03.2016, 07:56
Кандидат Javascript-наук
Отправить личное сообщение для Strongman Посмотреть профиль Найти все сообщения от Strongman
 
Регистрация: 22.03.2016
Сообщений: 132

Если честно не понял, что Ваш код делает. Опишите, пожалуйста, поподробнее. У меня появились просто цветные полоски с надписями "text(цифра)" и все. Никакой анимации, ничего нет.
А вот интересно, что это за конструкция такая:
return{
init: function(elem){}
left: function(elem) {}
/*и т.д.*/}

Это что, обращаться к выдаваемому результату, как к полям объекта? И ведь ошибки никакой не выдает, собака!
Ответить с цитированием
  #3 (permalink)  
Старый 22.03.2016, 08:13
Аватар для destus
Профессор
Отправить личное сообщение для destus Посмотреть профиль Найти все сообщения от destus
 
Регистрация: 18.05.2011
Сообщений: 1,207

Цитата:
А вот интересно, что это за конструкция такая:
функция возвращает объект, переменные width, бла-бла-бла берутся из замыкания.
Цитата:
И ведь ошибки никакой не выдает, собака!
и не должен
Ответить с цитированием
  #4 (permalink)  
Старый 22.03.2016, 10:26
Новичок на форуме
Отправить личное сообщение для Meshock Посмотреть профиль Найти все сообщения от Meshock
 
Регистрация: 21.03.2016
Сообщений: 4

Анимации автоматической и не должно быть — рехнешься, когда на странице будут автоматом "каруселить", скажем, 5 таких огромных слайдеров
"Цветные полоски" (слайды class="slide") сдвигаются влево/вправо только после клика по дивам class="arrow". Если бы код выдавал ошибку, я бы ее исправил , но ошибок в консоли нет, поэтому не знаю куда двигаться дальше
Да, и криво начинает срабатывать при множественном нажатии на направляющих див class="arrow".

добавлю еще CSS, чтобы верстка не ехала у вас
.case__container {
  height: 700px;
  width: 100%;
  overflow: hidden; }
  /* line 15, E:/Web projects/mikejuice/src/scss/layout/_portfolio-section.scss */
  .case__container .slider-wrap {
    position: relative;
    width: 1100px;
    margin: 0 auto; }
    /* line 20, E:/Web projects/mikejuice/src/scss/layout/_portfolio-section.scss */
    .case__container .slider-wrap .slider {
      position: absolute;
      width: 4400px;
      display: -webkit-box;
      display: -webkit-flex;
      display: -ms-flexbox;
      display: flex;
      z-index: 1; }
      /* line 26, E:/Web projects/mikejuice/src/scss/layout/_portfolio-section.scss */
      .case__container .slider-wrap .slider .slide {
        height: 700px;
        width: 1100px; }
      /* line 31, E:/Web projects/mikejuice/src/scss/layout/_portfolio-section.scss */
      .case__container .slider-wrap .slider .slide-first {
        margin-left: 0; }

/* line 38, E:/Web projects/mikejuice/src/scss/layout/_portfolio-section.scss */
.arrow {
  width: 40px;
  height: 40px;
  background-color: green;
  position: absolute;
  margin-top: 330px;
  z-index: 2; }

/* line 47, E:/Web projects/mikejuice/src/scss/layout/_portfolio-section.scss */
.arrow-left {
  left: 40px; }

/* line 51, E:/Web projects/mikejuice/src/scss/layout/_portfolio-section.scss */
.arrow-right {
  right: 40px; }


UPD Может попробовать координаты margin-left записывать в data-* тегов и считывать как-то оттуда? Есть идеи?

Последний раз редактировалось Meshock, 22.03.2016 в 11:52.
Ответить с цитированием
  #5 (permalink)  
Старый 22.03.2016, 13:30
Кандидат Javascript-наук
Отправить личное сообщение для Strongman Посмотреть профиль Найти все сообщения от Strongman
 
Регистрация: 22.03.2016
Сообщений: 132

По поводу Вашей задачи, ну у меня вообще стрелки не помещаются на экране по вертикали, чтобы, как Вы говорили, начать запуск второго до окончания остановки первого. Но я еще до Вашего сообщения начал понимать, что там примерно происходит. Вы говорите нет ошибок, есть! Две ошибки:
1) Uncaught TypeError: Cannot set property 'marginLeft' of undefined - происходит при нажатии на стрелку вправо, возникает в строке:
(position > -(count-1)*width) ? Slider.animateRight(tPosition,elem) : elem.style.marginLeft = position + 'px';
функции right;
2) Uncaught TypeError: wrap.getElem is not a function - возникает в строке:
wrap.getElem().style.marginLeft = tPosition + 'px';
или это последняя строка функции animateRight.
Многовато написали, задача довольно простая, мне кажется можно было проще написать.
Ответить с цитированием
  #6 (permalink)  
Старый 22.03.2016, 13:36
Новичок на форуме
Отправить личное сообщение для Meshock Посмотреть профиль Найти все сообщения от Meshock
 
Регистрация: 21.03.2016
Сообщений: 4

Сообщение от Strongman Посмотреть сообщение
По поводу Вашей задачи, ну у меня вообще стрелки не помещаются на экране по вертикали, чтобы, как Вы говорили, начать запуск второго до окончания остановки первого. Но я еще до Вашего сообщения начал понимать, что там примерно происходит. Вы говорите нет ошибок, есть! Две ошибки:
1) Uncaught TypeError: Cannot set property 'marginLeft' of undefined - происходит при нажатии на стрелку вправо, возникает в строке:
(position > -(count-1)*width) ? Slider.animateRight(tPosition,elem) : elem.style.marginLeft = position + 'px';
функции right;
2) Uncaught TypeError: wrap.getElem is not a function - возникает в строке:
wrap.getElem().style.marginLeft = tPosition + 'px';
или это последняя строка функции animateRight.
Многовато написали, задача довольно простая, мне кажется можно было проще написать.
Я утром исправил код, который привел в первом сообщении: забыл убрать wrap.getElem().style.marginLeft.
Но множественное нажатие на любую из стрелок все так же ломает анимацию. Думаю куда загрузить, чтобы вы живой пример глянули...

UPD Можно пощупать тут http://meshock.github.io/mj/

Последний раз редактировалось Meshock, 22.03.2016 в 15:17.
Ответить с цитированием
  #7 (permalink)  
Старый 22.03.2016, 16:53
Кандидат Javascript-наук
Отправить личное сообщение для Strongman Посмотреть профиль Найти все сообщения от Strongman
 
Регистрация: 22.03.2016
Сообщений: 132

А, ну дак нормально работает, остается только убрать блевотный зеленый цвет с кнопок и нарисовать в фотошопе красивые кнопки, как в Эксплорере, т.е. нужно стыбзить их оттуда. Для того, чтобы нажать на слайдер снизу, пока идет верхний, должна быть очень хорошая реакция. Так вообще это нереально сделать. Можно увеличить скорость прокрутки, чтобы это было вообще нереально сделать.
Можете, кстати, про заблокировать нижнюю кнопку пока идет верхний слайдер, ну и наоборот.
Ответить с цитированием
  #8 (permalink)  
Старый 22.03.2016, 17:34
Новичок на форуме
Отправить личное сообщение для Meshock Посмотреть профиль Найти все сообщения от Meshock
 
Регистрация: 21.03.2016
Сообщений: 4

Сообщение от Strongman Посмотреть сообщение
А, ну дак нормально работает, остается только убрать блевотный зеленый цвет с кнопок и нарисовать в фотошопе красивые кнопки, как в Эксплорере, т.е. нужно стыбзить их оттуда. Для того, чтобы нажать на слайдер снизу, пока идет верхний, должна быть очень хорошая реакция. Так вообще это нереально сделать. Можно увеличить скорость прокрутки, чтобы это было вообще нереально сделать.
Можете, кстати, про заблокировать нижнюю кнопку пока идет верхний слайдер, ну и наоборот.
А еже ли потыкать несколько раз быстро на кнопку? На том же jQuery тыкни дважды - он сделает анимацию один раз, потом за ним сделает второй раз, без глюков с высчитыванием конечной позиции
Ответить с цитированием
Ответ



Опции темы Искать в теме
Искать в теме:

Расширенный поиск


Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Анимация с скрытием слайдера при прокрутки вверх+привязка к кукам mylifegod Events/DOM/Window 9 17.04.2015 10:55
Анимация gif картинки при нажатии на ссылку ainur777 Общие вопросы Javascript 2 06.07.2014 16:23
Два слайдера на странице с одинаковыми классами работают одновременно. SlafkoCe jQuery 4 14.12.2012 12:44
Подружить два скрипта (скроллер+скрипт эффекта при наведении) Che jQuery 26 29.08.2012 10:59
Два блока div разъезжаются при скроллинге окна браузера. call007 jQuery 0 03.04.2011 16:21