Ограничение направления прокрутки от вертикали / горизонтали на той же странице - PullRequest
0 голосов
/ 12 января 2020

Я пытаюсь совершить sh тот же переход от вертикальной к горизонтальной прокрутке, который видели здесь .

Однако, прокрутка на горизонтальной секции, когда обе секции видны, включит горизонтальная прокрутка. Есть ли способ включить горизонтальную прокрутку и ограничить вертикальную прокрутку только тогда, когда вертикальная секция не видна? Извинения за неудобную формулировку; по сути, я бы хотел, чтобы красная часть прокручивалась только тогда, когда белая часть уже не видна.

$(window).scroll(function () {
  var scrollTop = $(window).scrollTop();
    if (scrollTop >= 1000){
      $("html, body").mousewheel(function(event, delta) {
          this.scrollLeft -= (delta * 30);
          $("html,body").toggleClass("disable-scroll");
       });
    }
});
#outsidescrollwrapper{
	width: 100vh;
	height: 100vw;
	transform: rotate(-90deg) translateX(-100vh);
	transform-origin: top left;
	overflow-y: scroll;
	overflow-x: hidden;
	position: absolute;
}
::-webkit-scrollbar {
	display: none;
}
.sidescrollwrapper{
	display: flex;
	flex-direction: row;
	width: 200vw;
	transform: rotate(90deg) translateY(-100vh);
	transform-origin: top left;
}
.sidescrollwrapper > .sidescroll {
	width: 100vw;
	height: 100vh;
}
#about{
  height: 1000px;
	background: linear-gradient(to bottom, #FBFDFF, white);
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div id="about">
</div>
<div id="outsidescrollwrapper">
	<div class="sidescrollwrapper">
		<div style="background-color:blue" class="sidescroll"></div>
		<div style="background-color:red" class="sidescroll"></div>
	</div>
</div>

https://jsfiddle.net/1h4yeac0/

1 Ответ

0 голосов
/ 13 января 2020

Я написал этот фрагмент ниже, в котором рассматриваются элементы, использующие атрибут data-direction. Значения этих атрибутов могут быть любыми, но я решил дать им либо horizontal, либо vertical значение, которое может быть направлением прокрутки, которое вы можете использовать.

Это будет контролировать только элементы что вы запрашиваете с аргументом selector и не изменит направление прокрутки. Эта часть, которую я оставляю на ваше усмотрение.

callback сработает всякий раз, когда в окне просмотра есть только 1 элементов Наблюдатель (что Вы просили, я полагаю). Этот обратный вызов имеет параметр, который является текущим значением направления. На основании этого значения вы можете переключать направления прокрутки.

Надеюсь, это поможет вам, мужик.

/**
 * Observes elements that indicate the current 
 * scroll-direction based on a data-direction attribute.
 * The callbacks fires with the current direction whenever 
 * a single observed element is in view.
 *
 * @param {string} selector
 * @param {function} callback
 * @returns {IntersectionObserver}
 */
function directionObserver(selector, callback) {

  /**
   * Store elements that are in view in a Set and 
   * set the default direction.
   */
  const elementsInView = new Set();
  let currentDirection = 'vertical';

  /**
   * Callback that runs whenever observed
   * elements intersect.
   *
   * @param {IntersectionObserverEntry[]} entries
   */
  const intersectionCallback = entries => {

    /**
     * Check if current entries are in view.
     * If they are add them to the elementsInView array
     * and remove them if they are not.
     */
    entries.forEach(entry => {
      const { target } = entry;
      if (entry.isIntersecting) {
        elementsInView.add(target);
      } else {
        elementsInView.delete(target);
      }
    });

    /**
     * Whenever there is only one element in the view
     * switch the currentDirection to the value of the
     * direction data attribute.
     */
    if (elementsInView.size === 1) {
      for (const element of elementsInView.values()) {
        currentDirection = element.dataset.direction;
        if ('function' === typeof callback) {
          callback(currentDirection);
        }
      }
    }

  }

  /**
   * Options for the observer
   */
  const options = {
    root: null,
    rootMargin: '50px 0px',
    threshold: [0, 1]
  };

  /**
   * Create observer
   */
  const observer = new IntersectionObserver(intersectionCallback, options);

  /**
   * Observer elements based on the selector argument
   */
  const sections = document.querySelectorAll(selector);
  sections.forEach(section => observer.observe(section));
  
  return currentDirection;
  
}

// Use the observer and observe all the .section elements.
directionObserver('.section', direction => {
  console.log(`Current direction is: ${direction}`);
  // Change scroll direction based on direction value.
});
*, *::before, *::after {
  margin: 0;
  padding: 0;
  box-sizing: border-box;
}

.section {
  display: block;
  height: 100vh;
  margin: 50px 0;
}

.vertical {
  width: 100%;
  background: repeating-linear-gradient(
    0deg, 
    white, 
    white 50px, 
    red 50px, 
    red 100px
   );
}

.horizontal {
  width: 300vw;
  background: repeating-linear-gradient(
    90deg, 
    white, 
    white 50px, 
    blue 50px, 
    blue 100px
   );
}
<div class="section vertical" data-direction="vertical"></div>
<div class="section horizontal" data-direction="horizontal"></div>
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...