Angular 8 滚动到片段,不会将片段带到页面顶部

Angular 8 scroll to a fragment, doesn't bring the fragment to the top of the page

我有一个 link,通过单击 link,我想滚动到页面底部的片段。当我单击 link 时,该片段正在运行,但没有将其带到页面顶部。

我尝试使用 div 和带有 id 的部分来创建片段。但是,它不会将 div 或部分带到页面顶部。

我的应用程序路由模块中的代码是:

 imports: [
    RouterModule.forRoot(routes, {
    //useHash: true,
    scrollPositionRestoration: 'enabled',
    onSameUrlNavigation: 'reload',
    anchorScrolling: 'enabled'
  })]

我的 link 和片段的组件代码:

<a [routerLink]="['/proposal']" fragment="dcn">{{ dcn }}</a>

<section id="dcn">
Some other html here
</section>

请注意,我已尝试使用 useHash:true,但它似乎不起作用。我希望没有 useHash 的解决方案是正确的。

我使用这样的代码滚动到元素:

HTML:

<button (click)="scroll(target)"></button>
<div #target>Your target</div>

TS:

scroll(el: HTMLElement) {
    el.scrollIntoView();
}

也许这对你有帮助。

切记:要页面滚动到元素,页面必须有足够的内容才能生成一个scroll/scrollbar,否则没有内容滚动。

我遇到了同样的情况,这是我所做的:

这是我的菜单组件上的 link:

<a class="dropdown-item" routerLink="/products" fragment="product-one">Product One</a>

这就是它在我的产品组件上的声明方式... product.component.html

  <div class="anchor">
    <a name="product-one"></a>
    <h2 >Product One</h2><br>
  </div>

product.component.css

.anchor a {
    position: absolute;
    left: 0px;
    top: -10em;
  }
.anchor {
    position: relative;
  }

product.component.ts:

  //TODO: Needs to verify if is necessary to declare Router and ActivatedRoute
  constructor( router: Router,
    private route:ActivatedRoute,) {
   }

算上CSS的top属性相当于菜单的大小。这样,当滚动发生时,它应该在菜单 div.

正下方显示锚定元素

希望对您有所帮助...

我已通过实施自定义滚动恢复行为.

解决了这个问题

此行为的原因是页面尚未呈现并且 scrollToPosition 没有效果。

没有关于超时的好 hack,但它有效。

export class AppModule {
  constructor(router: Router, viewportScroller: ViewportScroller) {
    router.events.pipe(
      filter((e): e is Scroll => e instanceof Scroll)
    ).subscribe(e => {
      if (e.position) {
        // backward navigation
        setTimeout(() => {viewportScroller.scrollToPosition(e.position); }, 0);
      } else if (e.anchor) {
        // anchor navigation
        setTimeout(() => {viewportScroller.scrollToAnchor(e.anchor); }, 0);
      } else {
        // forward navigation
        setTimeout(() => {viewportScroller.scrollToPosition([0, 0]); }, 0);
      }
    });
  }
}

我的情况略有不同,但我也在寻找与 useHash: true 类似的解决方案。

我采用了指令方法,下面是代码。

指令

@Directive({
  selector: '[ScrollIntoViewOnClick]'
})
export class ScrollIntoViewOnClickDirective {
  constructor(private _elementRef: ElementRef) { }

  @HostListener('click', ['$event.target'])
  scrollIntoView() {
    setTimeout(() => {
      document.getElementById(this._elementRef.nativeElement.dataset.sectionId).scrollIntoView({ behavior: 'smooth', block: 'start', inline: 'nearest' });
    }, 200)
  }

  scroll(el: HTMLElement) {
    el.scrollIntoView();
  }
}

HTML

<!-- click on here -->
<a href="javascript:void(0)"
   [attr.data-sectionId]="sectionId"
   ScrollIntoViewOnClick>
  Link
</a>

<!-- section to scroll -->
<section #{{sectionId}}
         [id]="sectionId">
  content
</section>

希望这会有所帮助:)

编码愉快...