# SweetAlert2
- SweetAlert2 (opens new window) is a popular JavaScript library that provides:
- Toast messages e.g. when a record is successfully deleted from or updated in the database
- Popup confirmation dialog box e.g. when deleting a record from the database
- To use SweetAlert2 in a Laravel project, you need to install the npm package (as a dev dependency) and create a JavaScript file that imports the SweetAlert2 library
# Install SweetAlert2
- Start by installing SweetAlert2 with the terminal command:
npm install sweetalert2 --save-dev
# Preparation
- Create a JavaScript file sweetAlert2.js in the
resources/js
folder - Open the resources/js/app.js file and add import sweetAlert2.js at the end of the file
... import './sweetAlert2';
Copied!
1
2
3
2
3
- Open the JavaScript file resources/js/sweetAlert2.js
- Import the SweetAlert2 library
- Add the SweetAlert2 library (
Swal
) to the window object
import Swal from 'sweetalert2'; window.Swal = Swal;
Copied!
1
2
2
- Now you can use SweetAlert2 on every page of your application
- The disadvantage of this approach is that you have to write the full Swal 'fire' method every time you want to use SweetAlert2
- To avoid this, you can create a default configuration for a toast message and for a popup confirmation dialog box and overwrite the default configuration when needed
- This keeps the code DRY (Don't Repeat Yourself) and makes our code in the components and Blade files more readable and a lot shorter
# Toast message
- Add the following code to the sweetalert2.js file:
- This code creates a default toast message with the SweetAlert2 library
- Line 5: this function is called whenever an event with the name
swal:toast
is triggered - Line 7 - 18:
Swal.mixin()
contains the default configuration for our toast message - Line 20: calls the
convertAttributes()
function to convert some attributes of the event- The property
background
can contain, by default, any CSS color value (e.g.#ff0000
,red
,rgb(255, 0, 0)
,rgba(255, 0, 0, 0.5)
, ...) - But now we can also use some predefined names for the background color:
danger
,error
,warning
,primary
;info
andsuccess
(the wordsdanger
anderror
are converted to'rgb(254, 226, 226)'
etc.) - If the property
text
is set, the property will be transformed to the propertyhtml
and then removed
- The property
- Line 22: calls the
Toast.fire()
method and pass the configuration properties to show the actual toast message
- Line 5: this function is called whenever an event with the name
import Swal from "sweetalert2"; window.Swal = Swal; // toast with default settings and event listener window.addEventListener('swal:toast', event => { // default settings for toasts const Toast = Swal.mixin({ toast: true, position: 'top-end', background: 'white', showConfirmButton: false, timer: 3000, timerProgressBar: true, didOpen: (toast) => { toast.addEventListener('mouseenter', Swal.stopTimer) toast.addEventListener('mouseleave', Swal.resumeTimer) } }); // convert some attributes const Config = convertAttributes(event.detail); // override default settings or add new settings Toast.fire(Config); }); function convertAttributes(attributes) { // convert predefined 'words' to a real color switch (attributes.background) { case 'danger': case 'error': attributes.background = 'rgb(254, 226, 226)'; break; case 'warning': attributes.background = 'rgb(255, 237, 213)'; break; case 'primary': case 'info': attributes.background = 'rgb(207, 250, 254)'; break; case 'success': attributes.background = 'rgb(220, 252, 231)'; break; } // if the attribute 'text' is set, convert it to the attribute 'html' if (attributes.text) { attributes.html = attributes.text; delete attributes.text; } return attributes; }
Copied!
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
TIP
- All possible options for the toast message can be found on the SweetAlert2 website (opens new window)
- You need at least the
title
or thetext
/html
properties configured, otherwise the toast will be empty
- Some examples of how to use the toast message:
Vanilla JavaScript
Livewire component
Alpine.js
document.getElementById('btnToast').addEventListener('click', () => { window.dispatchEvent(new CustomEvent('swal:toast', { detail: { title:'Hello world', text: 'Message from vanilla js', icon: 'success', background: 'success', } })); });
Copied!
1
2
3
4
5
6
7
8
9
10
2
3
4
5
6
7
8
9
10
# Popup confirmation dialog box
- Add the following code to the sweetalert2.js file:
- This code creates a default popup confirmation dialog box with the SweetAlert2 library
- Line 8: this function is called whenever an event with the name
swal:confirm
is triggered - Line 10 - 23:
Swal.mixin()
contains the default configuration for the confirmation dialog box - Line 25 - 26: move the
next
property to thenextEvent
variable and delete it from theevent.detail
object - Line 28: cals the
convertAttributes()
function to convert some attributes of the event (see above) - Line 30: calls the
fire()
method and pass the configuration properties to show the actual confirmation dialog box - Line 31 - 39: the
fire()
method returns a promise- Line 33: if the promise is resolved, check if the value of
isConfirmed
is set totrue
(you clicked on the conform button ) and if the variableNextEvent
is set - If both conditions are true:
- Line 35: dispatch a Livewire event with
event
as the event name andparams
as the payload - Line 37: dispatch a browser event with
event
as the event name andparams
as the payload
- Line 35: dispatch a Livewire event with
- Line 33: if the promise is resolved, check if the value of
- Line 8: this function is called whenever an event with the name
import Swal from "sweetalert2"; window.Swal = Swal; // toast with default settings and event listener window.addEventListener('swal:toast', event => { ... }); // confirm modal with default settings and event listener window.addEventListener('swal:confirm', event => { // default settings for confirm modals const Confirm = Swal.mixin({ width: 600, position: 'center', backdrop: true, showCancelButton: true, cancelButtonText: 'Cancel', cancelButtonColor: 'silver', showConfirmButton: true, confirmButtonText: 'Yes', confirmButtonColor: 'rgb(31, 41, 55)', reverseButtons: true, allowEscapeKey: true, allowOutsideClick: true, }); // move the 'next' property to the 'nextEvent' variable and delete it from the 'event.detail' object const NextEvent = event.detail.next ; delete event.detail.next; // convert some attributes const Config = convertAttributes(event.detail); // override default settings or add new settings Confirm.fire(Config) .then(result => { // execute this function if the confirm button is clicked AND if a 'NextEvent' is not empty if (result.isConfirmed && NextEvent) { // dispatch a Livewire event with 'event' as the event name and 'params' as the payload window.Livewire.emit(NextEvent.event, NextEvent.params); // dispatch a browser event with 'closeModal' as the event name and 'params' as the payload window.dispatchEvent(new CustomEvent(NextEvent.event, NextEvent.params)); } }); }); function convertAttributes(attributes) { ...}
Copied!
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
- An example of how to use the popup confirmation dialog box:
(This example is a simplified version of how we delete a genre in this project)
step 1: Livewire view
step 2: Livewire component
(optional)
- When you click on the delete (trash) button, the confirmation dialog box is shown
- The property
next
contains the event name (event
) and the payload (params
) that will be dispatched when the confirm button is clicked - If the cancel button is clicked, the confirmation dialog box is closed and nothing happens
@click="$dispatch('swal:confirm', { html: 'Delete {{ $genre->name }}?', cancelButtonText: 'NO!', confirmButtonText: 'YES DELETE THIS GENRE', next: { event: 'delete-genre', params: { id: {{ $genre->id }} } } })"
Copied!
1
2
3
4
5
6
7
8
9
10
11
2
3
4
5
6
7
8
9
10
11