单击导航栏链接时的水平滚动

问题描述

我刚刚开始编码,我在某个地方遇到了问题,我对JavaScript的了解很少,可能太简单了,我做不到。我正在尝试建立一个水平滚动的网站。我已经使用按钮完成了转换,但是 我想使用导航栏中的链接进行转换 当我单击导航链接时,我想要转到其他部分。 我该怎么办?

HTML代码

 <div class="navbar">
        <a href="" class="logo">
            <img src="" alt="" class="logo-img">
        </a>
        <nav class="nav-list">
            <a href="#home" class="nav-link home-btn">HOME</a>
            <a href="#about" class="nav-link about-btn">ABOUT</a>
            <a href="#portfolio" class="nav-link port-btn">PORTFOLIO</a>
        </nav>
    </div>

    <button class="page-btn left-btn">
        <i class="fa fa-arrow-left" aria-hidden="true"></i>
    </button>
    <button class="page-btn right-btn">
        <i class="fa fa-arrow-right" aria-hidden="true"></i>
    </button>

 
        <section class="section-1" id="home">
                <div class="section-title">
                    <h1 class="section-1-hd">
                        SECTION ONE
                    </h1>
                </div>
        </section>
        <section class="section-2" id="about">
                <div class="section-title">
                    <h1 class="section-2-hd">
                        SECTION TWO
                    </h1>
                </div>
        </section>
        <section class="section-3" id="portfolio">
                <div class="section-title">
                    <h1 class="section-3-hd">
                        SECTION THREE
                    </h1>
                </div>
        </section>

Javascript代码

var counter1 = 0;
var counter2 = 1;


const sections = document.querySelectorAll('section');

  if(counter1 === 3) {
    Array.from(sections).forEach(section =>{
      section.style.left = "0"
    })
    counter1=0;
    counter2=1;
   
}

  if(counter1 === -1) {
    Array.from(sections).forEach(section =>{
      if(section.classList[0] === 'section-3') {
        return;
      }
      section.style.left ='-100vw'
    })
    counter1=2;
    counter2=3;
   

  };

window.addEventListener('wheel',(e) =>{
  const deltaY = e.deltaY > 0;

  if(deltaY) {
    counter1++;
    counter2++;
  }else {
    counter1--;
    counter2--;
  }

  console.log(counter1,counter2);

  document.querySelector(`.section-${deltaY ? counter1 : counter2}`).style.left = `${deltaY ? "-100vw" : "0"}`;
  });


  document.querySelector('.left-btn').addEventListener('click',() => {
    counter1--;
    counter2--;
   document.querySelector(`.section-${counter2}`).style.left = '0';
  });

  document.querySelector('.right-btn').addEventListener('click',() => {
    counter1++;
    counter2++;
    document.querySelector(`.section-${counter1}`).style.left = '-100vw';
  });


我可能写了一个非常糟糕的代码,并为此道歉。

解决方法

首先,我们将所有section元素存储到一个数组中

const sections = document.querySelectorAll('section');

然后,创建一个函数,该函数将导航或将当前滚动x位置设置为下一部分或上一部分。

let index = 0;
function navigate(direction) {
  if (direction === 'next') {
    index = ++index % sections.length;
  }
  if (direction === 'prev') {
    index = (index > 0) ? --index : index;
  }

  window.scrollTo(sections[index].getBoundingClientRect().left,0);
}

此函数将当前部分的索引增加1,并通过sections数组的大小将其模量;如果其大于0,则将其减少1。

获取新的部分索引后,我们使用window.scrollTo(x,y)导航到目标部分left属性。

现在,我们已经完成了javascript,让我们回到HTML。与使用eventListener相比,使用onclick这样更容易

<button class="page-btn left-btn" onclick="navigate('prev')">
  prev
  <i class="fa fa-arrow-left" aria-hidden="true"></i>
</button>
<button class="page-btn right-btn" onclick="navigate('next')">
  next
<i class="fa fa-arrow-right" aria-hidden="true"></i>
</button>

onclick中,我们以{next”或“ prev”作为参数传递navigate函数

就在那里!

编辑:为此行

index = (index > 0) ? --index : index;

这等效于此

if (index > 0) {
    --index;
}
,

如果您愿意使用jquery,我可以从我自己的工具箱中为您提供一个功能。给定一个周围的容器,您的导航项是要滚动到其上的子元素。

包含jquery(有效期至2020/14/09):

<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.5.1/jquery.min.js"></script>

具有javascript函数进行滚动。像这样,使用.animate(..)

/** Will center the scroll-bar of a container onto one of his child elements horizontally.
 * @param id_container: id string of the scrollable container.
 * @param id_target   : id string of the target that is to be centered to.
 *   Should be a child of above container.
 * @param additional_offset: Will be added to the movement computation (pixels).
 * @param scroll_time: Number. Time in ms that the transition should take. 200 is a good value. */
function scroll_to(id_container,id_target,additional_offset,scroll_time)
{
  //> Preliminaries. -------------------------------------------------
  if (additional_offset===undefined) { additional_offset=0; }
  if (scroll_time===undefined) { scroll_time=200; }
  var cont = $("#"+id_container);
  var target = $("#"+id_target);
  //< ----------------------------------------------------------------
  //> Actual strolling scrolling. ------------------------------------
  var site = target.position().left + additional_offset - cont.innerWidth()/2.0 + cont.scrollLeft();
  cont.animate({ scrollLeft: site },scroll_time);
  //< ----------------------------------------------------------------
}

顺便说一句:整个动画内容实际上只是一点点糖。核心解决方案是在周围的容器scrollLeft上设置CSS属性。参见例如此处: https://developer.mozilla.org/en-US/docs/Web/API/Element/scrollLeft

相关问答

错误1:Request method ‘DELETE‘ not supported 错误还原:...
错误1:启动docker镜像时报错:Error response from daemon:...
错误1:private field ‘xxx‘ is never assigned 按Alt...
报错如下,通过源不能下载,最后警告pip需升级版本 Requirem...