Чи можу я програмно переміщати сходинки килимка-горизонтального кроку в кутовому / кутовому матеріалі


85

У мене запитання щодо кутового матеріалу (з Angular 4+). Скажімо, у моєму шаблоні компонента я додаю <mat-horizontal-stepper>компонент, і на кожному кроці у <mat-step>мене є крокові кнопки для навігації по компоненту. Як так ...

<mat-horizontal-stepper>
  <mat-step>
    Step 1
    <button mat-button matStepperPrevious type="button">Back</button>
    <button mat-button matStepperNext type="button">Next</button>
  </mat-step>
  <mat-step>
    Step 2
    <button mat-button matStepperPrevious type="button">Back</button>
    <button mat-button matStepperNext type="button">Next</button>
  </mat-step>
  <mat-step>
    Step 3
    <button mat-button matStepperPrevious type="button">Back</button>
    <button mat-button matStepperNext type="button">Next</button>
  </mat-step>
</mat-horizontal-stepper>

Зараз мені цікаво, чи можливо видалити кнопки з кожного кроку і розмістити їх де-небудь в <mat-horizontal-stepper>статичному положенні або навіть поза, <mat-horizontal-stepper>і я можу переміщатися вперед і назад, використовуючи код у моєму файлі машинописного компонента. Щоб дати уявлення, я хотів би, щоб мій HTML був приблизно таким

<mat-horizontal-stepper>
    <mat-step>
        Step 1
    </mat-step>
    <mat-step>
        Step 2
    </mat-step>
    <mat-step>
        Step 3
    </mat-step>
    <!-- one option -->
    <div>
       <button mat-button matStepperPrevious type="button">Back</button>
       <button mat-button matStepperNext type="button">Next</button>
    </div>
</mat-horizontal-stepper>

<!-- second option -->
<div>
   <button (click)="goBack()" type="button">Back</button>
   <button (click)="goForward()" type="button">Next</button>
</div>

Відповіді:


173

Так. Можна перейти до певного степпера, використовуючи selectedIndexвластивість MatStepper. Крім того, MatStepperвикриває публічні методи next()та previous(). Ви можете використовувати їх для переміщення вперед і назад.

У вашому шаблоні:

Додайте ідентифікатор у ваш степер, наприклад #stepper. Потім у вашому goBack()і goForward()методах передайте ідентифікатор кроку:

<mat-horizontal-stepper #stepper>
    <!-- Steps -->
</mat-horizontal-stepper>    
<!-- second option -->
<div>
   <button (click)="goBack(stepper)" type="button">Back</button>
   <button (click)="goForward(stepper)" type="button">Next</button>
</div>

.. а у вашому машинописі:

import { MatStepper } from '@angular/material/stepper';

goBack(stepper: MatStepper){
    stepper.previous();
}

goForward(stepper: MatStepper){
    stepper.next();
}

Посилання на демо-версію стека .


Ви також можете використовувати, ViewChildщоб отримати посилання на степпер-компонент у вашому TypeScript, як показано нижче:

@ViewChild('stepper') private myStepper: MatStepper;

goBack(){
    this.myStepper.previous();
}

goForward(){
    this.myStepper.next();
}

У цьому випадку вам не потрібно передавати посилання на крок у методі в html вашого компонента. Посилання на демонстрацію з ViewChild


Ви можете ввімкнути / вимкнути кнопки Backі Next, використовуючи такі дані:

<button (click)="goBack(stepper)" type="button" 
        [disabled]="stepper.selectedIndex === 0">Back</button>
<button (click)="goForward(stepper)" type="button" 
        [disabled]="stepper.selectedIndex === stepper._steps.length-1">Next</button>

8
Я просто дивився ViewChildі бачив, як я можу посилатись на Степпер - але ти мене до цього побив! Подобається той факт, що ви також додали функцію вимкнення / увімкнення! Є кілька пунктів!
Mike Sav

ViewChildтакож хороший варіант отримати степпер. Але я б віддав перевагу передачі посвідчення особи. Я також додав ViewChildрішення в демо \ o /
Faisal

Привіт, Фейсал, дякую за таку чудову відповідь, ще одну допомогу, замість того, щоб передати форму на мат-крок, ми можемо передавати кутові компоненти, а потім, залежно від дійсності цього компонента, чи можу я перейти до наступного етапу мат, як цього можна досягти , спасибі
Enthu

Гарне рішення. Але як ми могли обмежити область прокрутки лише вмістом степера, а не фактичним заголовком. Якщо ви додасте купу вмісту, тоді заголовок прокрутиться з поля зору. Оскільки заголовок вказує, де знаходиться користувач у якомусь процесі, тоді важливо, щоб заголовок був видимим незалежно від кількості вмісту на кожному кроці.
Wayne Riesterer

Тут для піктограм виконаних кроків встановлено значення "РЕДАКТУВАТИ", а для піктограм поточних кроків встановлено значення "ЧИСЛО". Чи можу я мати значок виконаних кроків як "ВИКОНАНО (галочка)", а коли натиснута кнопка "Назад" піктограму завершеного кроку змінили на "Редагувати" .... НАПРИМІР: припустимо, що я закінчив крок 2 і натиснув на наступну кнопку, тепер піктограма кроку 2 відображається як "ЗМІНИТИ піктограму (символ ручки)", і тепер я переходжу до кроку 3, який показує "Число" як піктограму .... Що Я хочу зробити, коли при наступному натисканні btn із кроку 2 піктограма має бути "ВИКОНАНО", а піктограма 3-го кроку має бути "Число", якщо я натиснув btn 3-го кроку, значок 3-го кроку повинен бути "Зроблено" 2-й «РЕДАГУВАТИ».
Чжу,

29

На додаток до відповіді @ Faisal , це мій погляд на те, щоб MatStepper стрибав без необхідності передавати крок в аргументах.

Це корисно, коли вам потрібна більша гнучкість у маніпулюванні степпером, наприклад, з a Serviceабо чогось іншого.

HTML:

<div fxLayout="row" fxLayoutAlign="center center" fxLayoutGap="6px">
  <button (click)="move(0)">1st</button>
  <button (click)="move(1)">2nd</button>
  <button (click)="move(2)">3rd</button>
  <button (click)="move(3)">4th</button>
</div>

Файл TS:

move(index: number) {
    this.stepper.selectedIndex = index;
}

Ось демо-версія стека .


21

Якщо ви хочете перейти програмно до наступного кроку і якщо ви використовуєте лінійний степпер , виконайте наступні кроки:

  • Створіть stepperтакий: <mat-horizontal-stepper linear #matHorizontalStepper>
  • Визначте mat-stepтак:<mat-step [completed]="isThisStepDone">
  • Зсередини mat-stepстворіть кнопку, щоб перейти до наступного кроку таким чином: <button (click)="next(matHorizontalStepper)">NEXT STEP</button>
  • У .tsфайлі оголосіть MatStepperпосилання з ім'ям степпер :
    @ViewChild('matHorizontalStepper') stepper: MatStepper;
  • Крім того, всередині .tsфайлу ініціалізується isThisStepDoneяк false :isThisStepDone: boolean = false;
  • Потім напишіть метод для кнопки NEXT STEP з назвою next():

    submit(stepper: MatStepper) {
     this.isThisStepDone = true;
     setTimeout(() => {           // or do some API calls/ Async events
      stepper.next();
     }, 1);
    }
    

3
Асинхронна частина ( setTimeout()) потрібна через поширення стану через isThisStepDone.
Юрій

2

Ви також можете це зробити, вказавши фактичний індекс степпера за допомогою selectedIndex.

stackblitz: https://stackblitz.com/edit/angular-4rvy2s?file=app%2Fstepper-overview-example.ts

HTML:

<div class="fab-nav-container">
   <mat-vertical-stepper linear="false" #stepper>
       <mat-step *ngFor="let step of stepNodes; let i = index">
           <ng-template matStepLabel>
               <p> {{step.title}} </p>
           </ng-template>
       </mat-step>
   </mat-vertical-stepper>
</div>

<div class="button-container">
   <div class="button-grp">
      <button mat-stroked-button (click)="clickButton(1, stepper)">1</button>
      <button mat-stroked-button (click)="clickButton(2, stepper)">2</button>
      <button mat-stroked-button (click)="clickButton(3, stepper)">3</button>
   </div>
</div>

TS:

import {Component, OnInit, ViewChild} from '@angular/core';
import {FormBuilder, FormGroup, Validators} from '@angular/forms';
import { MatVerticalStepper } from '@angular/material';
import { MatStepper } from '@angular/material';
export interface INodes {
    title: string;
    seq: number;
    flowId: string;
}
/**
 * @title Stepper overview
 */
@Component({
  selector: 'stepper-overview-example',
  templateUrl: 'stepper-overview-example.html',
  styleUrls: ['stepper-overview-example.scss'],
})
export class StepperOverviewExample implements OnInit {
  @ViewChild(MatVerticalStepper) vert_stepper: MatVerticalStepper;
  @ViewChild('stepper') private myStepper: MatStepper;

  stepNodes: INodes[] = [
    { title: 'Request Submission', seq: 1, flowId: 'xasd12'}, 
    { title: 'Department Approval', seq: 2, flowId: 'erda23'}, 
    { title: 'Requestor Confirmation', seq: 3, flowId: 'fsyq51'}, 
  ];

  ngOnInit() {
  }
  ngAfterViewInit() {
    this.vert_stepper._getIndicatorType = () => 'number';
  }
  clickButton(index: number, stepper: MatStepper) {
      stepper.selectedIndex = index - 1;
  }
}

1
Я просто використовую @ViewChild('stepper') private myStepper: MatStepper;і ніж this.matStepper.next();у своїй функції. Працює ідеально
Макс
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.