<template>
<div v-show="isLayerVisible" class="alerts_layer" @click="clearMessage()">
<div
v-for="item in messages"
:key="item.id"
:class="getAlertClassname(item.type)"
role="alert"
>
<strong v-text="$te(item.title) ? $t(item.title) : item.title" />
<p v-html="getMessageText(item)" />
<button
type="button"
class="close"
aria-label="Close"
@click="dismissMessage($event, item.id)"
>
<span aria-hidden="true">×</span>
</button>
</div>
</div>
</template>
<script>
import api from '../../api'
import { mapGetters } from 'vuex'
import Vue from 'vue'
/**
* @namespace components
* @category components
* @subcategory shared
* @module AlertsLayer
**/
export default {
mixins: [Vue.$mixins.authMixin],
data() {
return {
isLayerVisible: false,
}
},
computed: {
...mapGetters({
messages: 'alert/alerts',
}),
},
watch: {
messages(messages) {
if (messages.length > 0) {
//If login view: message should contains "Login" or "Auth" as part of the title
if (
this.$route.name === 'login_screen' &&
!messages.find(
(m) =>
!!['auth', 'login'].find((str) =>
m.title.toLowerCase().includes(str)
)
)
) {
this.clearMessage()
this.isLayerVisible = false
} else {
//For any other route, show messages right away
this.isLayerVisible = true
}
} else {
this.isLayerVisible = false
}
},
},
created() {
api.bus.$on('403', () => {
if (!this.messages.find((v) => v.title === '403')) {
this.$store.dispatch('alert/addAlert', {
type: 'warning',
title: '403',
text: 'alerts.NOT_ENOUGH_RIGHTS',
})
}
})
api.bus.$on('401', () => {
if (
!this.messages.find((v) => v.title === '401') &&
this.$route.name !== 'login_screen'
) {
this.$store.dispatch('alert/addAlert', {
type: 'warning',
title: 'session.token_expired_message_title',
text: 'session.token_expired_message_contents',
})
this.logoutFromApplication()
//A session expired event can left some loader hanging around
setTimeout(() => {
this.$loader.hide()
}, 1000)
}
})
this.dismissInterval = setInterval(() => {
let lastMessage = this.messages[this.messages.length - 1]
if (lastMessage && lastMessage.dismissible) {
this.countDownChanged(lastMessage)
if (lastMessage.dismissCountDown <= 0) {
this.clearMessage()
}
}
}, 1000)
/*
:dismissible="item.dismissible"
@dismissed="clearMessage"
@dismiss-count-down="countDownChanged(item)"
*/
},
destroyed() {
window.clearInterval(this.dismissInterval)
},
methods: {
countDownChanged(item) {
if (item.dismissCountDown === undefined) {
item.dismissCountDown = item.dismissSecs || 5
}
item.dismissCountDown--
},
getMessageText(item) {
return this.$t(item.text, item.params || {})
},
dismissMessage(e, id) {
e && e.stopPropagation()
this.$store.dispatch('alert/removeAlert', id)
},
getAlertClassname(type) {
return `alert alert-${type} alert-dismissible fade show`
},
/**
* @todo Clear all messages if multiple
*/
clearMessage() {
if (this.messages.length > 0) {
this.dismissMessage(null, this.messages[this.messages.length - 1].id)
}
},
},
}
</script>
<style lang="scss" scoped>
.alerts_layer {
position: absolute;
left: 0px;
top: 0px;
width: calc(100vw);
height: calc(100vh);
z-index: 9999999999;
background-color: rgba(255, 255, 255, 0.5);
}
</style>
Source