Javascript 如何使用Vue路由器创建定位标记

Javascript 如何使用Vue路由器创建定位标记,javascript,html,vue.js,Javascript,Html,Vue.js,我正在创建一个小webapp,我想在此创建一个锚定标记 我给了一个id给一个div我想要像这样的锚定标签: <div id="for-home"> .... </div> 但是有了这个锚定标记,有时有效,有时无效,我是否错过了一些东西?我相信你是在问,通过导航到页面中的锚定标记(如#section-3),直接跳到页面的特定区域 要使其工作,您需要修改scrollBehavior函数,如下所示: 新VueRouter({ 模式:“历史”, 滚动行为:函数(到、从、保

我正在创建一个小webapp,我想在此创建一个锚定标记

我给了一个
id
给一个
div
我想要像这样的锚定标签:

<div id="for-home">
   ....
</div>

但是有了这个锚定标记,有时有效,有时无效,我是否错过了一些东西?

我相信你是在问,通过导航到页面中的锚定标记(如
#section-3
),直接跳到页面的特定区域

要使其工作,您需要修改scrollBehavior函数,如下所示:

新VueRouter({
模式:“历史”,
滚动行为:函数(到、从、保存位置){
if(to.hash){
返回{selector:to.hash}
//或者对于Vue 3:
//返回{el:to.hash}
}否则{
返回{x:0,y:0}
}
},
路线:[
{路径:'/',组件:abcView},
//你的路线
]
});
参考:

我试图创建一个JSFIDLE示例,但由于
模式:'history'
而无法工作。如果复制代码并在本地运行,您将看到它是如何工作的:


通过在scrollBehavior中返回
{selector:to.hash}
(或Vue 3中的
{el:to.hash}
),您将把锚定标记哈希传递到下一个路由,该路由将导航到相关部分(使用
id
标记)在这个过程中。

我也遇到了这个问题,我认为有一点空间可以优化页面交换。就我而言,我希望平稳过渡,而不是“跳来跳去”。我已经在jQuery中要求使用$的别名

这是我的路由器设置的平滑动画,请随意修改线,以您的需要相应。这段代码可以变得更干净,但应该足够好,可以向您展示工作思路

// Register Router and Paths
const router = new VueRouter({
    mode: 'history',
    routes : [
        { path: '/aboutme/', component: index, name:'me.index'},
        { path: '/aboutme/cv', component: cv, name:'me.cv' }
    ],

    // Build smooth transition logic with $
    scrollBehavior (to, from, savedPosition) {
       if (to.hash) {
          return $('html,body').stop().animate({scrollTop: $(to.hash).offset().top }, 1000);
       } else {
          return $('html,body').stop().animate({scrollTop: 0 }, 500);
       }
    }
})
我这边的附带问题:我们必须归还什么吗?由于jQuery动画正在处理页面滚动,因此返回或不返回都没有任何问题


关于Gkiokan

如果您需要制作动画scrollTo,请使用vue scrollTo软件包:设置非常简单


文档和代码的示例可以在这里找到:

对于我来说,
{selector:to.hash}
解决方案拒绝与vue router 4.0.0一起使用。下面的方法起作用了,还支持平滑滚动

500毫秒的超时允许页面加载,因为我发现,否则平滑滚动将无法滚动到正确的位置(因为页面仍在加载)


我试过亚当·赖斯的答案,它是有效的。但是我觉得当你刷新页面时,与原来的
return{selector:to.hash}
相比,它有点不好。因此,我尝试了一种不同的方法,使用promise。它的工作原理与原版相同

代码如下:

函数滚动行为(到、从、保存位置){
如果(保存位置){
返回保存的位置
}
if(to.hash){
返回新承诺((解决、拒绝)=>{
设置超时(()=>{
解析({selector:to.hash})
}, 300)
})
}
返回新承诺((解决、拒绝)=>{
设置超时(()=>{
解析({x:0,y:0})
}, 300)
})
}
我认为问题在于哈希路由在页面完全加载之前执行。这就是为什么它什么也不做,因为还没有显示id为的元素。但我不知道为什么如果我刷新页面,效果会很好。无论如何,这是我的解决方案。我希望这对任何新来者都有帮助

注:

  • 这段代码可以很好地导航到不同的页面或同一页面。根据需要调整超时时间
  • 为了平滑导航,我只使用CSS。在具有滚动的根元素/元素上,可以添加
    滚动行为:平滑以使其平滑,如上所述
  • 我使用了vue路由器3.5.1,因为我仍然使用vue 2.x。如果您使用VUE3,您可以按照rits在Adam Reis的回答中所说的那样调整代码

这是否仅在历史记录模式下有效?我不能让它工作,但我不在历史模式是的,页面明确提到这一点。原因是您已经将哈希标识符绑定到路由器状态。不可能使用第二个散列来标识页面位置(滚动到锚点)。另一个选项是在路由中传递
query
参数,然后使用普通的旧javascript滚动到目标页面中的正确位置。我没有一个有效的例子来展示,但我相信如果我们花一些时间在上面,它是可以做到的。哦,是的,它确实清楚地提到了这一点。我发誓我对粗体的音符有一个盲点。谢谢你用Nuxtjs安装了吗?如果是的话,是如何做到的?我试图得到一个意外的错误关键字变量。不,我没有使用Nuxtjs。在clear SSR上,它的设置非常简单:app.js从“vue scrollto”导入VueScrollTo;使用(VueScrollTo,{duration:800,ease:'ease in out',offset:-60,});你好我是一个很好的人。对于vue 3,
return{el:to.hash}
而不是
return{selector:to.hash}
有效。这看起来确实有效,可惜没有文档记录!谢谢@rits!!您应该用此评论编辑已接受的答案!我就这么做了@Benjaminfourgeau
// Register Router and Paths
const router = new VueRouter({
    mode: 'history',
    routes : [
        { path: '/aboutme/', component: index, name:'me.index'},
        { path: '/aboutme/cv', component: cv, name:'me.cv' }
    ],

    // Build smooth transition logic with $
    scrollBehavior (to, from, savedPosition) {
       if (to.hash) {
          return $('html,body').stop().animate({scrollTop: $(to.hash).offset().top }, 1000);
       } else {
          return $('html,body').stop().animate({scrollTop: 0 }, 500);
       }
    }
})
const scrollBehavior = (to, from, savedPosition) => {
  if (to.hash) {
    setTimeout(() => {
      const element = document.getElementById(to.hash.replace(/#/, ''))
      if (element && element.scrollIntoView) {
        element.scrollIntoView({block: 'end', behavior: 'smooth'})
      }
    }, 500)

    //NOTE: This doesn't work for Vue 3
    //return {selector: to.hash}

    //This does
    return {el: to.hash};
  }
  else if (savedPosition) {
    return savedPosition
  }
  return {top: 0}
}