34

I am a bit confused about the usage of [mat-dialog-close].

So, I have a dialog with a form. If the user clicks the submit button, the form is validated. If the input is valid, the dialog is closed and the form is submitted. However, if the input is invalid, the dialog remains opened and an error message is shown. For that I want to use [mat-dialog-close] as it is described in the official documentation where it is used as follows:

<button mat-button [mat-dialog-close]="true">Yes</button>

I thought that I can just pass it a boolean and whether the tag is active depends on the boolean value of the variable. However, this does not work. I tried it like this:

<button type="submit" (click)="addUser()" [mat-dialog-close]="formisvalid" mat-button>Submit</button>

I passed it the variable formisvalid. It's value is true unless the input is invalid. But now the dialog closes always, regardless of the value of formisvalid. I also tried replacing it with false. I thought the dialog would remain opened no matter what happens, but it would also always close.

So, my question is: am I mistaken about the use of [mat-dialog-close] or am I just doing something wrong? If this is not achievable with the [mat-dialog-close] directive, what would be another way to achieve what I'm trying to do?

Laura L.
  • 401
  • 1
  • 4
  • 7
  • 1
    Don't use it with []. Ex.: `` – blixenkrone Dec 06 '17 at 13:27
  • But why would they implement it then, if I'm not supposed to use it? There has to be a use for it, doesn't it? – Laura L. Dec 06 '17 at 13:44
  • What do you mean? You import it in your component and app.module.ts, and then you call the button in the HTML component as in my example – blixenkrone Dec 06 '17 at 17:15
  • Yes, this works, but not as I want it to. If I do it like you described, then the dialog will close always when I press the save button. I want it to only close when the form is valid, otherwise it is supposed to stay opened. – Laura L. Dec 07 '17 at 13:08
  • 2
    Import the MatDialogRef class and in the constructor: `public dialogRef: MatDialogRef,`. Then call dialogRef.afterClose(*somecode*). – blixenkrone Dec 07 '17 at 13:19
  • Set an if-statement that checks if the form is valid f.ex if(form.value === 'VALID').. – blixenkrone Dec 07 '17 at 13:20

7 Answers7

33

Set your button to have disabled on it if the form is not valid. This way the button cannot be clicked unless the form is valid, meaning it won't close unless the form is valid

<button type="submit" (click)="addUser()" mat-dialog-close [disabled]="formisvalid" mat-button>Submit</button>
Joo Beck
  • 1,863
  • 1
  • 18
  • 21
  • 1
    it is some workaround, but can I easily close dialog from inside the dialog component. I have httpClient request in onSubmit method and I would like to close or not the dialog depending on the result. If I have the successful result in subscribe method I will close the dialog. Otherwise I will leave it with some warning message displayed. – Michał Ziobro Dec 21 '17 at 13:23
  • 11
    yeah, you would have `constructor(public dialogRef: MatDialogRef) { }` on your constructor, and then just `this.dialogRef.close(returnValue);` – Joo Beck Dec 21 '17 at 20:49
25

Just to make the answer complete: mat-dialog-close will close your dialog if it's clicked, no matter what value you assign to it. If you want to control whether clicking it will close the dialog, use [disabled]="formisvalid" as [other answer] states.

However the value assigned to mat-dialog-close is not ignored. It's interpreted as the dialog result value, and as such can be read by the component that opened the dialog, by subscribing to dialogRef.afterClosed(). This behaviour is explained in the official documentation:

Torinthiel
  • 970
  • 1
  • 8
  • 15
10

Since this caused confusion for a lot of developers: if you want to perform requests on close and/or trigger the close with a custom element (instead of a basic button), you can inject a reference to the dialog and then call .close:

constructor(public dialogRef: MatDialogRef<DialogComponent>) { } - replace DialogComponent with your component name

Then define a method on your component class and call it in your template:

async closeDialog() {
    try {
      await someAsyncThing();
      this.dialogRef.close(); // make sure it only closes if the upper async fn succesfully ran!
    } catch(e) {
      this.errorMessage = e.response.message;
    }
}

<fancy-ass-close-item (click)="closeDialog()"/>

As opposed to other answers here, this enables you to call requests before closing the dialog (and thus display an error message or something inside the dialog).

sandrooco
  • 8,016
  • 9
  • 48
  • 86
8

uses of mat-dialog-close(applicable for dialog)

1.to prevents accidental form submits.

<form #queryForm="ngForm" (ngSubmit)="saveQuery()">
    <button mat-button (click)="close()">Cancel</button>
    <!--ended up by submitting the form instead of calling close function, -->
    <!--So you should add mat-dialog-close to prevent it-->
<form>

2.to close dialog.

<button mat-button mat-dialog-close>close</button>
<!--closes dialog even without explicit function-->

3.to return data.

<button mat-button mat-dialog-close="myData">close</button>

Add to the component:

dialogRef.afterClosed().subscribe(data=>{
    console.log("data returned from mat-dialog-close is ",data);
})
SwissCodeMen
  • 4,222
  • 8
  • 24
  • 34
5

Here you can pass any number of values as a array to an attribute [mat-dialog-close]

<button [mat-dialog-close]="[organizationId,costCenterId,partnerDepartmentId]" cdkFocusInitial class="iport_primary_btn"mat-raised-button>Go</button>

In parent component you can subscribe to the result after closing dialog like below

dialogRef.afterClosed().subscribe(result => {
console.log(result);
});
Sagar M
  • 1,168
  • 13
  • 10
0

mat-dialog-close directive only works with button element and not any other one.

Bluerain
  • 477
  • 5
  • 9
  • this is not true, I've tried it on other element and it worked well – Rafi Henig Aug 25 '20 at 14:59
  • [Dox](https://material.angular.io/components/dialog/overview#dialog-content) says "mat-dialog-close [Attr] Added to a – LosManos Jan 08 '21 at 15:13
-1
constructor(
    public dialogRef: MatDialogRef<OffersComponent>
  ) {}

and right it down close() function where u want to close the ur dialog box

 this.dialogRef.close();
Sushil
  • 670
  • 7
  • 14