Skip to content

Commit f52e5d2

Browse files
committed
feat:Initialized CustomToast component
1 parent e5ec12f commit f52e5d2

File tree

5 files changed

+113
-15
lines changed

5 files changed

+113
-15
lines changed

src/App.vue

+10-8
Original file line numberDiff line numberDiff line change
@@ -1,15 +1,17 @@
11
<template>
22
<RouterView />
3-
<VToasts/>
3+
<VToasts />
4+
<CustomToast />
45
</template>
56

67
<script>
7-
// Components
8-
import VToasts from '@/components/VToasts.vue';
8+
// Components
9+
import VToasts from '@/components/VToasts.vue';
10+
import CustomToast from './components/comments/CustomToast.vue';
911
10-
export default {
11-
name: 'App',
12+
export default {
13+
name: 'App',
1214
13-
components: { VToasts }
14-
};
15-
</script>
15+
components: { VToasts, CustomToast }
16+
};
17+
</script>

src/components/VToasts.vue

-1
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,6 @@
2929
3030
export default {
3131
name: 'VToasts',
32-
3332
setup() {
3433
let items = installToast();
3534
+47
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,47 @@
1+
<template>
2+
<div class="toast-container bottom-0 end-0">
3+
<div v-for="item of items" :key="item.id"
4+
:class="`toast show align-items-center border-1 m-2 fw-medium text-bg-${item.theme}`" role="alert"
5+
aria-live="assertive" aria-atomic="true">
6+
<div class="toast-header" v-html="item.title" v-if="!!item.title"></div>
7+
<div class="d-flex justify-content-between align-items-center">
8+
<div class="toast-body">
9+
<button @click="handleCallbackCall" class="btn btn-secondary">
10+
Undo
11+
</button>
12+
</div>
13+
<button v-if="item.clearable" type="button" class="btn-close p-3" aria-label="Close"
14+
@click="hideToast(item.id)"></button>
15+
</div>
16+
</div>
17+
</div>
18+
</template>
19+
20+
<script>
21+
import { installCustomToast, useCustomToast } from '@/composables/customToast.composable';
22+
23+
export default {
24+
name: 'CustomToast',
25+
setup(props) {
26+
let items = installCustomToast();
27+
28+
const { hideToast } = useCustomToast();
29+
const handleCallbackCall = () => {
30+
props?.callbackFn?.()
31+
hideToast()
32+
}
33+
34+
return {
35+
items,
36+
hideToast,
37+
handleCallbackCall
38+
};
39+
},
40+
props: {
41+
callbackFn: {
42+
type: Function,
43+
}
44+
}
45+
46+
}
47+
</script>
+52
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
import { ref, getCurrentInstance } from 'vue';
2+
3+
// Utils
4+
import { getUniqueId } from '@/utils';
5+
6+
const items = ref([]);
7+
8+
export function installCustomToast() {
9+
const instance = getCurrentInstance();
10+
if (instance.type.name !== 'CustomToast') {
11+
throw new Error('installToast should only be called in the Custom toast component');
12+
}
13+
14+
return items;
15+
}
16+
17+
export function useCustomToast() {
18+
function showToast({ body, theme, duration = 5000, clearable = true , title}) {
19+
const id = getUniqueId();
20+
21+
const _timeOutId = setTimeout(function () {
22+
hideToast(id);
23+
}, duration);
24+
25+
items.value.push({
26+
id,
27+
body,
28+
duration,
29+
theme,
30+
clearable,
31+
title,
32+
_time_out_id: _timeOutId
33+
});
34+
35+
return id;
36+
}
37+
38+
function hideToast(id) {
39+
const index = items.value.findIndex(function (item) {
40+
return item.id === id;
41+
});
42+
43+
clearTimeout(items.value[index]._time_out_id);
44+
45+
items.value.splice(index, 1);
46+
}
47+
48+
return {
49+
showToast,
50+
hideToast
51+
};
52+
}

src/views/CommentsView.vue

+4-6
Original file line numberDiff line numberDiff line change
@@ -109,16 +109,15 @@ import VModal from "@/components/VModal.vue";
109109
import { useFetchComments } from "@/composables/comments.composable";
110110
import { useApplyFilters } from "@/composables/filter.composable";
111111
import useFetchPost from "@/composables/posts.composable";
112-
import { useToast } from "@/composables/toast.composable";
112+
import { useCustomToast } from "@/composables/customToast.composable";
113113
import ThemeColor from "@/enums/ThemeColor";
114114
import StorageService from "@/services/storage.service";
115115
import { computed, reactive, ref, watch } from "vue";
116116
117117
export default {
118118
name: "CommentsView",
119119
setup() {
120-
const { showToast } = useToast();
121-
120+
const { showToast } = useCustomToast();
122121
const { comments, commentsIsLoading, fetchComments, changeStatus: changeCommentStatus } = useFetchComments();
123122
fetchComments({});
124123
@@ -196,20 +195,18 @@ export default {
196195
};
197196
const handleConfirmRejection = () => {
198197
changeCommentStatus(rejectComment.comment.id, "REJECTED");
199-
showToast({ body: "Undo", theme: ThemeColor.WARNING, duration: 3000 });
198+
showToast({ body:"Undo", theme: ThemeColor.WARNING, duration: 3000 });
200199
rejectComment.comment = null;
201200
rejectComment.modalIsOpen = false;
202201
};
203202
204203
const selectedRows = ref([]);
205-
206204
const handleStatusChangeAll = (status) => {
207205
selectedRows.value.forEach((commentId) => {
208206
changeCommentStatus(commentId, status);
209207
selectedRows.value = [];
210208
});
211209
};
212-
213210
return {
214211
comments: filteredComments,
215212
commentsIsLoading,
@@ -233,5 +230,6 @@ export default {
233230
CommentsFilterForm,
234231
VModal,
235232
},
233+
236234
};
237235
</script>

0 commit comments

Comments
 (0)