mirror of
https://github.com/Fabio286/antares.git
synced 2025-02-28 09:27:43 +01:00
feat: unsaved changes reminder
This commit is contained in:
parent
a4122b4eaa
commit
33d1fa2290
@ -17,6 +17,7 @@
|
|||||||
<TheNotificationsBoard />
|
<TheNotificationsBoard />
|
||||||
<ModalNewConnection v-if="isNewConnModal" />
|
<ModalNewConnection v-if="isNewConnModal" />
|
||||||
<ModalSettings v-if="isSettingModal" />
|
<ModalSettings v-if="isSettingModal" />
|
||||||
|
<ModalDiscardChanges v-if="isUnsavedDiscardModal" />
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
@ -35,7 +36,8 @@ export default {
|
|||||||
TheAppWelcome: () => import(/* webpackChunkName: "TheAppWelcome" */'@/components/TheAppWelcome'),
|
TheAppWelcome: () => import(/* webpackChunkName: "TheAppWelcome" */'@/components/TheAppWelcome'),
|
||||||
Workspace: () => import(/* webpackChunkName: "Workspace" */'@/components/Workspace'),
|
Workspace: () => import(/* webpackChunkName: "Workspace" */'@/components/Workspace'),
|
||||||
ModalNewConnection: () => import(/* webpackChunkName: "ModalNewConnection" */'@/components/ModalNewConnection'),
|
ModalNewConnection: () => import(/* webpackChunkName: "ModalNewConnection" */'@/components/ModalNewConnection'),
|
||||||
ModalSettings: () => import(/* webpackChunkName: "ModalSettings" */'@/components/ModalSettings')
|
ModalSettings: () => import(/* webpackChunkName: "ModalSettings" */'@/components/ModalSettings'),
|
||||||
|
ModalDiscardChanges: () => import(/* webpackChunkName: "ModalDiscardChanges" */'@/components/ModalDiscardChanges')
|
||||||
},
|
},
|
||||||
data () {
|
data () {
|
||||||
return {};
|
return {};
|
||||||
@ -46,7 +48,8 @@ export default {
|
|||||||
isNewConnModal: 'application/isNewModal',
|
isNewConnModal: 'application/isNewModal',
|
||||||
isEditModal: 'application/isEditModal',
|
isEditModal: 'application/isEditModal',
|
||||||
isSettingModal: 'application/isSettingModal',
|
isSettingModal: 'application/isSettingModal',
|
||||||
connections: 'connections/getConnections'
|
connections: 'connections/getConnections',
|
||||||
|
isUnsavedDiscardModal: 'workspaces/isUnsavedDiscardModal'
|
||||||
})
|
})
|
||||||
},
|
},
|
||||||
mounted () {
|
mounted () {
|
||||||
|
57
src/renderer/components/ModalDiscardChanges.vue
Normal file
57
src/renderer/components/ModalDiscardChanges.vue
Normal file
@ -0,0 +1,57 @@
|
|||||||
|
<template>
|
||||||
|
<ConfirmModal
|
||||||
|
:confirm-text="$t('word.discard')"
|
||||||
|
:cancel-text="$t('word.stay')"
|
||||||
|
@confirm="discardUnsavedChanges"
|
||||||
|
@hide="closeUnsavedChangesModal"
|
||||||
|
>
|
||||||
|
<template slot="header">
|
||||||
|
<div class="d-flex">
|
||||||
|
<i class="mdi mdi-24px mdi-content-save-alert mr-1" /> {{ $t('message.unsavedChanges') }}
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
<div slot="body">
|
||||||
|
<div>
|
||||||
|
{{ $t('message.discardUnsavedChanges') }}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</ConfirmModal>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
import { mapActions } from 'vuex';
|
||||||
|
import ConfirmModal from '@/components/BaseConfirmModal';
|
||||||
|
|
||||||
|
export default {
|
||||||
|
name: 'ModalDiscardChanges',
|
||||||
|
components: {
|
||||||
|
ConfirmModal
|
||||||
|
},
|
||||||
|
created () {
|
||||||
|
window.addEventListener('keydown', this.onKey);
|
||||||
|
},
|
||||||
|
beforeDestroy () {
|
||||||
|
window.removeEventListener('keydown', this.onKey);
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
...mapActions({
|
||||||
|
discardUnsavedChanges: 'workspaces/discardUnsavedChanges',
|
||||||
|
closeUnsavedChangesModal: 'workspaces/closeUnsavedChangesModal'
|
||||||
|
}),
|
||||||
|
closeModal () {
|
||||||
|
this.$emit('close');
|
||||||
|
},
|
||||||
|
onKey (e) {
|
||||||
|
e.stopPropagation();
|
||||||
|
if (e.key === 'Escape')
|
||||||
|
this.closeModal();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.modal-container {
|
||||||
|
max-width: 360px;
|
||||||
|
}
|
||||||
|
</style>
|
@ -67,6 +67,7 @@
|
|||||||
</ul>
|
</ul>
|
||||||
<WorkspacePropsTab
|
<WorkspacePropsTab
|
||||||
v-show="selectedTab === 'prop'"
|
v-show="selectedTab === 'prop'"
|
||||||
|
:is-selected="selectedTab === 'prop'"
|
||||||
:connection="connection"
|
:connection="connection"
|
||||||
:table="workspace.breadcrumbs.table"
|
:table="workspace.breadcrumbs.table"
|
||||||
/>
|
/>
|
||||||
|
@ -18,7 +18,7 @@
|
|||||||
:key="table.name"
|
:key="table.name"
|
||||||
class="menu-item"
|
class="menu-item"
|
||||||
:class="{'text-bold': breadcrumbs.schema === database.name && breadcrumbs.table === table.name}"
|
:class="{'text-bold': breadcrumbs.schema === database.name && breadcrumbs.table === table.name}"
|
||||||
@click="changeBreadcrumbs({schema: database.name, table: table.name})"
|
@click="setBreadcrumbs({schema: database.name, table: table.name})"
|
||||||
@contextmenu.prevent="showTableContext($event, table.name)"
|
@contextmenu.prevent="showTableContext($event, table.name)"
|
||||||
>
|
>
|
||||||
<a class="table-name">
|
<a class="table-name">
|
||||||
@ -76,6 +76,10 @@ export default {
|
|||||||
piePercentage (val) {
|
piePercentage (val) {
|
||||||
const perc = val / this.maxSize * 100;
|
const perc = val / this.maxSize * 100;
|
||||||
return { background: `conic-gradient(lime ${perc}%, white 0)` };
|
return { background: `conic-gradient(lime ${perc}%, white 0)` };
|
||||||
|
},
|
||||||
|
setBreadcrumbs (payload) {
|
||||||
|
if (this.breadcrumbs.schema === payload.schema && this.breadcrumbs.table === payload.table) return;
|
||||||
|
this.changeBreadcrumbs(payload);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
@ -137,7 +137,7 @@ export default {
|
|||||||
},
|
},
|
||||||
tableOptions () {
|
tableOptions () {
|
||||||
const db = this.workspace.structure.find(db => db.name === this.schema);
|
const db = this.workspace.structure.find(db => db.name === this.schema);
|
||||||
return db ? db.tables.find(table => table.name === this.table) : {};
|
return db && this.table ? db.tables.find(table => table.name === this.table) : {};
|
||||||
},
|
},
|
||||||
defaultEngine () {
|
defaultEngine () {
|
||||||
return this.getDatabaseVariable(this.connection.uid, 'default_storage_engine').value || '';
|
return this.getDatabaseVariable(this.connection.uid, 'default_storage_engine').value || '';
|
||||||
@ -167,12 +167,17 @@ export default {
|
|||||||
this.getFieldsData();
|
this.getFieldsData();
|
||||||
this.lastTable = this.table;
|
this.lastTable = this.table;
|
||||||
}
|
}
|
||||||
|
},
|
||||||
|
isChanged (val) {
|
||||||
|
if (this.isSelected && this.lastTable === this.table && this.table !== null)
|
||||||
|
this.setUnsavedChanges(val);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
methods: {
|
methods: {
|
||||||
...mapActions({
|
...mapActions({
|
||||||
addNotification: 'notifications/addNotification',
|
addNotification: 'notifications/addNotification',
|
||||||
refreshStructure: 'workspaces/refreshStructure'
|
refreshStructure: 'workspaces/refreshStructure',
|
||||||
|
setUnsavedChanges: 'workspaces/setUnsavedChanges'
|
||||||
}),
|
}),
|
||||||
async getFieldsData () {
|
async getFieldsData () {
|
||||||
if (!this.table) return;
|
if (!this.table) return;
|
||||||
|
@ -59,7 +59,9 @@ module.exports = {
|
|||||||
field: 'Field | Fields',
|
field: 'Field | Fields',
|
||||||
approximately: 'Approximately',
|
approximately: 'Approximately',
|
||||||
total: 'Total',
|
total: 'Total',
|
||||||
table: 'Table'
|
table: 'Table',
|
||||||
|
discard: 'Discard',
|
||||||
|
stay: 'Stay'
|
||||||
},
|
},
|
||||||
message: {
|
message: {
|
||||||
appWelcome: 'Welcome to Antares SQL Client!',
|
appWelcome: 'Welcome to Antares SQL Client!',
|
||||||
@ -111,7 +113,9 @@ module.exports = {
|
|||||||
createNewTable: 'Create new table',
|
createNewTable: 'Create new table',
|
||||||
emptyTable: 'Empty table',
|
emptyTable: 'Empty table',
|
||||||
deleteTable: 'Delete table',
|
deleteTable: 'Delete table',
|
||||||
emptyCorfirm: 'Do you confirm to empty'
|
emptyCorfirm: 'Do you confirm to empty',
|
||||||
|
unsavedChanges: 'Unsaved changes',
|
||||||
|
discardUnsavedChanges: 'You have some unsaved changes. By leaving this tab these changes will be discarded.'
|
||||||
},
|
},
|
||||||
// Date and Time
|
// Date and Time
|
||||||
short: {
|
short: {
|
||||||
|
@ -11,7 +11,9 @@ export default {
|
|||||||
state: {
|
state: {
|
||||||
workspaces: [],
|
workspaces: [],
|
||||||
selected_workspace: null,
|
selected_workspace: null,
|
||||||
has_unsaved_changes: false
|
has_unsaved_changes: false,
|
||||||
|
is_unsaved_discard_modal: false,
|
||||||
|
pending_breadcrumbs: {}
|
||||||
},
|
},
|
||||||
getters: {
|
getters: {
|
||||||
getSelected: state => {
|
getSelected: state => {
|
||||||
@ -36,6 +38,9 @@ export default {
|
|||||||
return state.workspaces
|
return state.workspaces
|
||||||
.filter(workspace => workspace.connected)
|
.filter(workspace => workspace.connected)
|
||||||
.map(workspace => workspace.uid);
|
.map(workspace => workspace.uid);
|
||||||
|
},
|
||||||
|
isUnsavedDiscardModal: state => {
|
||||||
|
return state.is_unsaved_discard_modal;
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
mutations: {
|
mutations: {
|
||||||
@ -176,6 +181,15 @@ export default {
|
|||||||
else
|
else
|
||||||
return workspace;
|
return workspace;
|
||||||
});
|
});
|
||||||
|
},
|
||||||
|
SET_UNSAVED_CHANGES (state, val) {
|
||||||
|
state.has_unsaved_changes = !!val;
|
||||||
|
},
|
||||||
|
SET_UNSAVED_DISCARD_MODAL (state, val) {
|
||||||
|
state.is_unsaved_discard_modal = !!val;
|
||||||
|
},
|
||||||
|
SET_PENDING_BREADCRUMBS (state, payload) {
|
||||||
|
state.pending_breadcrumbs = payload;
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
actions: {
|
actions: {
|
||||||
@ -294,8 +308,16 @@ export default {
|
|||||||
|
|
||||||
if (getters.getWorkspace(uid).tabs.length < 3)
|
if (getters.getWorkspace(uid).tabs.length < 3)
|
||||||
dispatch('newTab', uid);
|
dispatch('newTab', uid);
|
||||||
|
|
||||||
|
dispatch('setUnsavedChanges', false);
|
||||||
},
|
},
|
||||||
changeBreadcrumbs ({ commit, getters }, payload) {
|
changeBreadcrumbs ({ state, commit, getters }, payload) {
|
||||||
|
if (state.has_unsaved_changes) {
|
||||||
|
commit('SET_UNSAVED_DISCARD_MODAL', true);
|
||||||
|
commit('SET_PENDING_BREADCRUMBS', payload);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
const breadcrumbsObj = {
|
const breadcrumbsObj = {
|
||||||
schema: null,
|
schema: null,
|
||||||
table: null,
|
table: null,
|
||||||
@ -329,6 +351,18 @@ export default {
|
|||||||
},
|
},
|
||||||
setTabKeyUsage ({ commit }, payload) {
|
setTabKeyUsage ({ commit }, payload) {
|
||||||
commit('SET_TAB_KEY_USAGE', payload);
|
commit('SET_TAB_KEY_USAGE', payload);
|
||||||
|
},
|
||||||
|
setUnsavedChanges ({ commit }, val) {
|
||||||
|
commit('SET_UNSAVED_CHANGES', val);
|
||||||
|
},
|
||||||
|
discardUnsavedChanges ({ state, commit, dispatch }) {
|
||||||
|
dispatch('setUnsavedChanges', false);
|
||||||
|
dispatch('changeBreadcrumbs', state.pending_breadcrumbs);
|
||||||
|
commit('SET_UNSAVED_DISCARD_MODAL', false);
|
||||||
|
commit('SET_PENDING_BREADCRUMBS', {});
|
||||||
|
},
|
||||||
|
closeUnsavedChangesModal ({ commit }) {
|
||||||
|
commit('SET_UNSAVED_DISCARD_MODAL', false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
Loading…
x
Reference in New Issue
Block a user