web-dev-qa-db-ja.com

角度4-アンカーへのスクロール

同じページのアンカー要素に簡単なスクロールをしようとしています。基本的に、ユーザーは「Try It」ボタンをクリックし、「login」というIDを持つページの下の領域にスクロールします。現在、基本的なid="login"<a href="#login"></a>しかし、それはそのセクションにジャンプしています。理想的には、そこにスクロールしてほしい。私がAngular4を使用している場合、これを行うための方法がいくつか組み込まれていますか、最も簡単な方法は何ですか?ありがとう!

テンプレート全体...(コンポーネントはまだ空です)

<div id="image-header">
    <div id="intro">
        <h1 class="text-center">Welcome to ThinkPlan</h1>
        <h3 class="text-center">Planning your way</h3>
        <a class="btn btn-outline-primary" href="#login" id="view">Try It</a> <!-- Where the user clicks to scroll -->
    </div>
</div>
<div class="container" id="info">
    <div class="row">
        <div class="col-md-12">
             <div class="space" id="login"></div> <!-- The place to scroll to -->
                <h1 class="text-center">ThinkPlan</h1>
                <form  class="form-horizontal">
                    <fieldset>
                        <legend>Login</legend>
                        <div class="form-group">
                            <label for="inputEmail" class="col-lg-2 control-label">Email</label>
                            <div class="col-lg-10">
                                <input type="text" class="form-control" id="inputEmail" placeholder="Email">
                            </div>
                        </div>
                        <div class="form-group">
                            <label for="inputPassword" class="col-lg-2 control-label">Password</label>
                            <div class="col-lg-10">
                                <input type="password" class="form-control" id="inputPassword" placeholder="Password"> 
                            </div>
                        </div>
                        <div class="form-group" id="log-btn">
                            <div class="col-lg-10 col-lg-offset-2">
                                <button routerLink="/plan" type="submit" class="btn btn-outline-primary">Login</button>
                            </div>
                        </div>
                        <p class="lead text-center">New here? <a routerLink="signup">Sign up.</a></p>
                    </fieldset>
                </form>
        </div>
    </div>
</div>
19
lnamba

私はそれがより簡単な解決策だと思う:

HTMLで:

<a [routerLink]="['/']" fragment="login"></a>

TypeScriptで:

ngOnInit() {
 this.route.fragment.subscribe(fragment => { this.fragment = fragment; });
}

ngAfterViewChecked(): void {
  try {
      if(this.fragment) {
          document.querySelector('#' + this.fragment).scrollIntoView();
      }
  } catch (e) { }
}
17
Sarah Dubois

自動スクロール

Angular v6なので、anchorScrollingに新しいRouterModuleオプションがあります。モジュールのインポートで設定できます:

imports: [
  ...,
  RouterModule.forRoot(routes, {anchorScrolling: 'enabled'})

これにより、Angularは指定されたフラグメントのIDを持つ要素に自動的にスクロールします。

However️ただし、データが非同期にロードされる場合、これは機能しません。これを参照してください Githubの問題 。 ⚠️


手動スクロール

スムーズスクロールRouterModuleを介してまだ使用できませんが、手動で実行できます。

1)ターゲットを取得しますViewChildを使用:

@ViewChild('pageInfo') pageInfo: ElementRef; 

2)scrollIntoViewnativeElementを呼び出します。

const targetElement = this.pageInfo.nativeElement
targetElement.scrollIntoView({behavior: "smooth"})
13
Kim Kern

Angular 4を使用すると、同じページにアンカーを使用するときに問題が発生する可能性があります。

この方法で解決しました

ng2-page-scroll

インストール

npm install ng2-page-scroll --save

app.module.tsにインポートします

import {Ng2PageScrollModule} from 'ng2-page-scroll';

@NgModule({
    imports: [
        /* Other imports here */
        Ng2PageScrollModule
        ]
})
export class AppModule {
}

htmlコンポーネントでテストします

<a pageScroll href="#test">Testing</a>
<div id="test">

AfterViewCheck()ChangeDetectionがトリガーされるたびに呼び出されるため、これは悪い解決策です。

AfterViewInit()を使用

public ngAfterViewInit(): void {
  this.subscription = this.route.fragment
    .subscribe(fragment => {
        const targetElement = this.document.querySelector('#' + fragment);
        if (fragment && targetElement) {
            targetElement.scrollIntoView();
        } else {
            window.scrollTo(0, 0);
        }
    });
}
public ngOnDestroy(): void {
    this.subscription.unsubscribe();
}
2
Sergey Andreev

これは、上記のサラデュボアの答えに追加するより詳細な例です。

ルーターモジュールをインポートします。

import { ActivatedRoute, Router, NavigationEnd } from '@angular/router';

constructor(private route:ActivatedRoute, 
            private router:Router) {

  router.events.subscribe(event => {
    if (event instanceof NavigationEnd) {    
      if (event.url) {
        this.route.fragment.subscribe(fragment => this.fragment = fragment);
      }
    }
  });

}

ngAfterViewChecked(): void {

  try {
    if(this.fragment != null) {
     document.querySelector("a[name="+this.fragment+"]").scrollIntoView();
    }
  } catch (e) {
    //console.log(e, 'error');
  }

}

QuerySelectorを使用すると、スクロールする要素に多くのオプションが提供されます。 https://developer.mozilla.org/en-US/docs/Web/API/Document/querySelector

これはAngular 8 :)で動作します

0