Skip to content

Commit

Permalink
Replace similar toasts
Browse files Browse the repository at this point in the history
  • Loading branch information
mabdullahsari committed Nov 25, 2024
1 parent 8a9f12b commit d540f18
Show file tree
Hide file tree
Showing 7 changed files with 46 additions and 5 deletions.
6 changes: 6 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,12 @@

All notable changes to `livewire-toaster` will be documented in this file.

## 2.5.0 - 2024-11-25

### Added

- Replacement of similar toasts

## 2.4.0 - 2024-11-24

### Added
Expand Down
11 changes: 11 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -391,6 +391,17 @@ This way, your users will have enough time to read toasts that are a tad larger
So, if your base duration value is `3 seconds` and your toast contains 223 words,
the total on-screen duration of the toast will be `3 + 2 = 5 seconds`

### Replacing similar toasts

> [!NOTE]
> The `replace` configuration value must be set to `true`.
> [!WARNING]
> Takes precedence over `suppress`.
Toaster will dispose of any toast that is similar to the one being dispatched prior to displaying the new toast.
A toast is considered similar if it has the same `duration`, `message`, and `type`.

### Suppressing duplicate toasts

> [!NOTE]
Expand Down
8 changes: 8 additions & 0 deletions config/toaster.php
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,14 @@
*/
'position' => 'right',

/**
* New toasts immediately replace similar ones, ensuring only one toast of a kind is visible at any time.
* Takes precedence over the "suppress" option.
*
* Supported: true | false
*/
'replace' => true,

/**
* Prevent the display of duplicate toast messages.
*
Expand Down
5 changes: 3 additions & 2 deletions resources/js/config.js
Original file line number Diff line number Diff line change
Expand Up @@ -11,13 +11,14 @@ class Alignment {
}

export class Config {
constructor(alignment, duration, suppress) {
constructor(alignment, duration, replace, suppress) {
this.alignment = new Alignment(alignment);
this.duration = duration;
this.replace = replace;
this.suppress = suppress;
}

static fromJson(data) {
return new Config(data.alignment, data.duration, data.suppress);
return new Config(data.alignment, data.duration, data.replace, data.suppress);
}
}
4 changes: 3 additions & 1 deletion resources/js/hub.js
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,9 @@ export function Hub(Alpine) {
document.addEventListener('toaster:received', event => {
const toast = Toast.fromJson({ duration: config.duration, ...event.detail });

if (config.suppress && this.toasts.some(t => t.equals(toast))) {
if (config.replace) {
this.toasts.filter(t => t.equals(toast)).forEach(t => t.dispose());
} else if (config.suppress && this.toasts.some(t => t.equals(toast))) {
return;
}

Expand Down
10 changes: 9 additions & 1 deletion src/ToasterConfig.php
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ private function __construct(
public string $position,
public bool $wantsAccessibility,
public bool $wantsCloseableToasts,
public bool $wantsReplacement,
public bool $wantsSuppression,
public bool $wantsTranslation,
) {}
Expand All @@ -24,6 +25,7 @@ private function __construct(
* position?: "center" | "left" | "right",
* accessibility?: bool,
* closeable?: bool,
* replace?: bool,
* suppress?: bool,
* translate?: bool,
* } $config
Expand All @@ -36,6 +38,7 @@ public static function fromArray(array $config): self
Arr::get($config, 'position', 'right'),
Arr::get($config, 'accessibility', true),
Arr::get($config, 'closeable', true),
Arr::get($config, 'replace', false),
Arr::get($config, 'suppress', false),
Arr::get($config, 'translate', true),
);
Expand All @@ -53,6 +56,11 @@ public function position(): Position

public function toJavaScript(): array
{
return ['alignment' => $this->alignment, 'duration' => $this->duration, 'suppress' => $this->wantsSuppression];
return [
'alignment' => $this->alignment,
'duration' => $this->duration,
'replace' => $this->wantsReplacement,
'suppress' => $this->wantsSuppression,
];
}
}
7 changes: 6 additions & 1 deletion tests/ToasterConfigTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,11 @@ public function it_can_be_serialized_for_the_frontend(): void

$array = $config->toJavaScript();

$this->assertSame(['alignment' => 'bottom', 'duration' => 3000, 'suppress' => false], $array);
$this->assertSame([
'alignment' => 'bottom',
'duration' => 3000,
'replace' => false,
'suppress' => false,
], $array);
}
}

0 comments on commit d540f18

Please sign in to comment.