【问题标题】:Vue - Scroll To DivVue - 滚动到 Div
【发布时间】:2020-03-09 14:22:11
【问题描述】:

我想创建一个按钮,一旦点击,它就会滚动到特定的 div。

这是我的代码:

  <form @submit.prevent="onSubmit">
  <div class="form-group">
    <div class="col-md-6 employee_name">
      <label for="name">Name</label>
      <input
        type="text"
        name="name"
        class="name_input"
        placeholder="Enter your name"
        v-model="name"
        required
      />
    </div>
  </div>
  <div class="form-group">
    <div class="col-md-6 employee_email">
      <label for="email">Email</label>
      <input
        type="email"
        name="email"
        class="email_input"
        placeholder="Enter your email"
        required
      />
    </div>
  </div>
  <div class="form-group">
    <div class="col-md-6 employee_title">
      <label for="title">Title</label>
      <input
        type="text"
        name="title"
        class="title_input"
        placeholder="Enter your title"
        v-model="title"
        required
      />
    </div>
  </div>
  <div class="form-group">
    <button class="btn btn-light submit" type="submit" @submit="onSubmit>Submit</button>
  </div>
</form>

   <div id="main" class="container" v-if="infoComplete">
  <div class="col-md-12 primary_option">
    <h4 class="primary_lead">Please copy & paste signature inside the box below</h4>
    <div class="container desktop_container">
      <h5 class="email_style">Desktop</h5>
      <div class="col-md-7 desktop">
        <EmailSignature :name="name" :title="title" />
      </div>
    </div>
    <div class="container mobile_container">
      <h5 class="email_style">Mobile</h5>
      <div class="col-md-4 mobile">
        <MobileEmailSignature :name="name" :title="title" />
      </div>
    </div>
    <div class="col-md-6 secondary_option">
      <h2 class="secondary_lead">OR...</h2>
      <button class="btn btn-outline-light download_button" @click="onDownload">Download</button>
    </div>
  </div>
</div>

这是我的 onClick 函数:

onClick() {
  let elmnt = document.getElementById("main");
  elmnt.scrollIntoView({ behavior: "smooth" });
}

还有我的 onSubmit 函数:

 onSubmit() {
  console.log("Submitted");
  this.infoComplete = true;
},

虽然它有效,但它没有按正确的顺序执行。因此,在提交时,div 将显示。但是,如果我再次单击提交按钮,它将滚动到该 div。我需要它,所以一旦 div 显示在显示屏上,就立即滚动。有没有更好的方法来做到这一点?我无法确定我做错了什么。

【问题讨论】:

  • 你的onSubmit在模板代码的哪里?
  • @HankX 刚刚添加了它。

标签: javascript vue.js


【解决方案1】:

我过去做过一些事情,可以通过创建指令来完成。

const scroll = {
    bind(el, binding) {
        const handler = () => {
            setTimeout(function () {
                let element = el;

                if (typeof binding.value.el !== 'undefined') {
                    element = document.getElementById(binding.value.el)
                }

                let bodyRect = document.body.getBoundingClientRect(),
                    elementRect = element.getBoundingClientRect(),
                    offset = (elementRect.top - bodyRect.top) + (binding.value.offset || 0),
                    startingY = window.pageYOffset,
                    elementY = offset,
                    targetY,
                    diff,
                    easeInOutCubic,
                    start,
                    duration = (binding.value.speed || 500);

                // if element is close to page's bottom then window will scroll only to some position above the element...
                targetY = document.body.scrollHeight - elementY < window.innerHeight ? document.body.scrollHeight - window.innerHeight : elementY;
                diff = targetY - startingY;

                easeInOutCubic = function (t) {
                    return t < .5 ? 4 * t * t * t : (t - 1) * (2 * t - 2) * (2 * t - 2) + 1
                };

                if (!diff) return;

                // bootstrap our animation,
                //  it will get called right before next frame shall be rendered...
                window.requestAnimationFrame(function step(timestamp) {
                    if (!start) start = timestamp;

                    let time = timestamp - start, // elapsed milliseconds since start of scrolling...
                        percent = Math.min(time / duration, 1); // get percent of completion in range [0, 1]

                    // apply the easing, it can cause bad-looking
                    //  slow frames in browser performance tool, so be careful...
                    percent = easeInOutCubic(percent);

                    window.scrollTo(0, startingY + diff * percent);

                    // proceed with animation as long as we wanted it to.
                    if (time < duration) {
                        window.requestAnimationFrame(step)
                    }
                });
            }, 400);
        };

        let scrollOn = binding.value.scrollOn || null;

        if (scrollOn && scrollOn === 'init') {
            handler();
        } else {
            el.addEventListener('click', handler);
            el.$destroy = () => el.removeEventListener('click', handler);
        }
    },
    unbind: function (el) {
        if (typeof el.$destroy !== 'function') return;

        el.$destroy()
    }
};


new Vue({
  el: "#app",
  directives: {scroll: scroll}
})

请看这个jsFiddle

【讨论】:

    【解决方案2】:

    你可以通过简单地将滚动代码放在onSubmit函数中,添加一个setTimeout来等待页面渲染id="main"

    onSubmit() {
            console.log("Submitted");
            this.infoComplete = true;
            setTimeout(()=>{
              let elmnt = document.getElementById("main");
              elmnt.scrollIntoView({behavior: "smooth"});
            }, 100)
          },
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2011-07-14
      • 1970-01-01
      • 2011-06-21
      • 2015-10-11
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多