mirror of https://github.com/Fabio286/antares.git
Merge branch 'master' of https://github.com/antares-sql/antares into ts-renderer
This commit is contained in:
commit
33a4663694
|
@ -1,4 +1,4 @@
|
||||||
name: Build/release [linux]
|
name: Build/release [LINUX]
|
||||||
|
|
||||||
on: push
|
on: push
|
||||||
|
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
name: Build/release [mac]
|
name: Build/release [MAC]
|
||||||
|
|
||||||
on: push
|
on: push
|
||||||
|
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
name: Build/release [windows]
|
name: Build/release [WINDOWS]
|
||||||
|
|
||||||
on: push
|
on: push
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,26 @@
|
||||||
|
name: Create artifact [LINUX]
|
||||||
|
|
||||||
|
on:
|
||||||
|
workflow_dispatch: {}
|
||||||
|
|
||||||
|
jobs:
|
||||||
|
build:
|
||||||
|
runs-on: ubuntu-latest
|
||||||
|
steps:
|
||||||
|
- name: Check out Git repository
|
||||||
|
uses: actions/checkout@v3
|
||||||
|
|
||||||
|
- name: npm install & build
|
||||||
|
run: |
|
||||||
|
npm install
|
||||||
|
npm run build:local
|
||||||
|
|
||||||
|
- name: Upload Artifact
|
||||||
|
uses: actions/upload-artifact@v3
|
||||||
|
with:
|
||||||
|
name: linux-build
|
||||||
|
retention-days: 3
|
||||||
|
path: |
|
||||||
|
build
|
||||||
|
!build/*-unpacked
|
||||||
|
!build/.icon-ico
|
|
@ -1,4 +1,4 @@
|
||||||
name: Test end-to-end [linux]
|
name: Test end-to-end [LINUX]
|
||||||
|
|
||||||
on: push
|
on: push
|
||||||
|
|
||||||
|
|
|
@ -6,7 +6,8 @@
|
||||||
"PostgreSQL",
|
"PostgreSQL",
|
||||||
"SQLite",
|
"SQLite",
|
||||||
"Windows",
|
"Windows",
|
||||||
"translation"
|
"translation",
|
||||||
|
"Linux"
|
||||||
],
|
],
|
||||||
"svg.preview.background": "transparent"
|
"svg.preview.background": "transparent"
|
||||||
}
|
}
|
14
CHANGELOG.md
14
CHANGELOG.md
|
@ -2,6 +2,20 @@
|
||||||
|
|
||||||
All notable changes to this project will be documented in this file. See [standard-version](https://github.com/conventional-changelog/standard-version) for commit guidelines.
|
All notable changes to this project will be documented in this file. See [standard-version](https://github.com/conventional-changelog/standard-version) for commit guidelines.
|
||||||
|
|
||||||
|
### [0.5.6](https://github.com/antares-sql/antares/compare/v0.5.4...v0.5.6) (2022-06-02)
|
||||||
|
|
||||||
|
### Bug Fixes
|
||||||
|
|
||||||
|
* empty query tab schema select if no schema selected ([31b7999](https://github.com/antares-sql/antares/commit/31b7999bba5d115913d42087614b9888bc761068))
|
||||||
|
* inline field update not working with tables missing primary key ([caf776b](https://github.com/antares-sql/antares/commit/caf776bd55606c793c9763c204aa9f05d1feb27f))
|
||||||
|
* **SQLite:** unable to insert rows with TEXT fields ([a7d5e19](https://github.com/antares-sql/antares/commit/a7d5e1973cd59d7d0ef1e74bdcf44d87fba43559))
|
||||||
|
* **UI:** select closes clicking on scrollbar ([8870304](https://github.com/antares-sql/antares/commit/8870304c15346257a90193807b9ae07c1393e3e2))
|
||||||
|
|
||||||
|
|
||||||
|
### Improvements
|
||||||
|
|
||||||
|
* improved precision of MariaDB or MySQL auto detection ([26aad51](https://github.com/antares-sql/antares/commit/26aad519df6ea1bbc7dffbf540193a7b2ed9ae2a))
|
||||||
|
|
||||||
### [0.5.5](https://github.com/antares-sql/antares/compare/v0.5.4...v0.5.5) (2022-05-24)
|
### [0.5.5](https://github.com/antares-sql/antares/compare/v0.5.4...v0.5.5) (2022-05-24)
|
||||||
|
|
||||||
|
|
||||||
|
|
Binary file not shown.
After Width: | Height: | Size: 43 KiB |
10
package.json
10
package.json
|
@ -1,7 +1,7 @@
|
||||||
{
|
{
|
||||||
"name": "antares",
|
"name": "antares",
|
||||||
"productName": "Antares",
|
"productName": "Antares",
|
||||||
"version": "0.5.5",
|
"version": "0.5.6",
|
||||||
"description": "A modern, fast and productivity driven SQL client with a focus in UX.",
|
"description": "A modern, fast and productivity driven SQL client with a focus in UX.",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"repository": "https://github.com/antares-sql/antares.git",
|
"repository": "https://github.com/antares-sql/antares.git",
|
||||||
|
@ -13,7 +13,7 @@
|
||||||
"compile:workers": "webpack --mode=production --config webpack.workers.config.js",
|
"compile:workers": "webpack --mode=production --config webpack.workers.config.js",
|
||||||
"compile:renderer": "webpack --mode=production --config webpack.renderer.config.js",
|
"compile:renderer": "webpack --mode=production --config webpack.renderer.config.js",
|
||||||
"build": "cross-env NODE_ENV=production npm run compile",
|
"build": "cross-env NODE_ENV=production npm run compile",
|
||||||
"build:local": "npm run build && electron-builder",
|
"build:local": "npm run build && electron-builder --publish never",
|
||||||
"build:appx": "npm run build:local -- --win appx",
|
"build:appx": "npm run build:local -- --win appx",
|
||||||
"rebuild:electron": "rimraf ./dist && npm run postinstall",
|
"rebuild:electron": "rimraf ./dist && npm run postinstall",
|
||||||
"release": "standard-version",
|
"release": "standard-version",
|
||||||
|
@ -82,6 +82,12 @@
|
||||||
"license": "./LICENSE",
|
"license": "./LICENSE",
|
||||||
"category": "Development"
|
"category": "Development"
|
||||||
},
|
},
|
||||||
|
"nsis": {
|
||||||
|
"license": "./LICENSE",
|
||||||
|
"installerIcon": "assets/icon.ico",
|
||||||
|
"uninstallerIcon": "assets/icon.ico",
|
||||||
|
"installerHeader": "assets/icon.ico"
|
||||||
|
},
|
||||||
"portable": {
|
"portable": {
|
||||||
"artifactName": "${productName}-${version}-portable.exe"
|
"artifactName": "${productName}-${version}-portable.exe"
|
||||||
},
|
},
|
||||||
|
|
|
@ -169,6 +169,8 @@ export default (connections: {[key: string]: antares.Client}) => {
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
const { orgRow } = params;
|
const { orgRow } = params;
|
||||||
|
delete orgRow._antares_id;
|
||||||
|
|
||||||
reload = true;
|
reload = true;
|
||||||
|
|
||||||
for (const key in orgRow) {
|
for (const key in orgRow) {
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
import { app, BrowserWindow, /* session, */ nativeImage, Menu } from 'electron';
|
import { app, BrowserWindow, /* session, */ nativeImage, Menu, ipcMain } from 'electron';
|
||||||
import * as path from 'path';
|
import * as path from 'path';
|
||||||
import * as Store from 'electron-store';
|
import * as Store from 'electron-store';
|
||||||
import * as windowStateKeeper from 'electron-window-state';
|
import * as windowStateKeeper from 'electron-window-state';
|
||||||
|
@ -7,9 +7,13 @@ import * as remoteMain from '@electron/remote/main';
|
||||||
import ipcHandlers from './ipc-handlers';
|
import ipcHandlers from './ipc-handlers';
|
||||||
|
|
||||||
Store.initRenderer();
|
Store.initRenderer();
|
||||||
|
const persistentStore = new Store({ name: 'settings' });
|
||||||
|
|
||||||
|
const appTheme = persistentStore.get('application_theme');
|
||||||
const isDevelopment = process.env.NODE_ENV !== 'production';
|
const isDevelopment = process.env.NODE_ENV !== 'production';
|
||||||
const isMacOS = process.platform === 'darwin';
|
const isMacOS = process.platform === 'darwin';
|
||||||
|
const isLinux = process.platform === 'linux';
|
||||||
|
const isWindows = process.platform === 'win32';
|
||||||
const gotTheLock = app.requestSingleInstanceLock();
|
const gotTheLock = app.requestSingleInstanceLock();
|
||||||
|
|
||||||
process.env.ELECTRON_DISABLE_SECURITY_WARNINGS = 'true';
|
process.env.ELECTRON_DISABLE_SECURITY_WARNINGS = 'true';
|
||||||
|
@ -19,7 +23,7 @@ let mainWindow: BrowserWindow;
|
||||||
let mainWindowState: windowStateKeeper.State;
|
let mainWindowState: windowStateKeeper.State;
|
||||||
|
|
||||||
async function createMainWindow () {
|
async function createMainWindow () {
|
||||||
const icon = require('../renderer/images/logo-32.png');
|
const icon = require('../renderer/images/logo-64.png');
|
||||||
const window = new BrowserWindow({
|
const window = new BrowserWindow({
|
||||||
width: mainWindowState.width,
|
width: mainWindowState.width,
|
||||||
height: mainWindowState.height,
|
height: mainWindowState.height,
|
||||||
|
@ -28,15 +32,21 @@ async function createMainWindow () {
|
||||||
minWidth: 900,
|
minWidth: 900,
|
||||||
minHeight: 550,
|
minHeight: 550,
|
||||||
title: 'Antares SQL',
|
title: 'Antares SQL',
|
||||||
autoHideMenuBar: true,
|
|
||||||
icon: nativeImage.createFromDataURL(icon.default),
|
icon: nativeImage.createFromDataURL(icon.default),
|
||||||
webPreferences: {
|
webPreferences: {
|
||||||
nodeIntegration: true,
|
nodeIntegration: true,
|
||||||
contextIsolation: false,
|
contextIsolation: false,
|
||||||
spellcheck: false
|
spellcheck: false
|
||||||
},
|
},
|
||||||
frame: false,
|
autoHideMenuBar: true,
|
||||||
titleBarStyle: isMacOS ? 'hidden' : 'default',
|
titleBarStyle: isLinux ? 'default' :'hidden',
|
||||||
|
titleBarOverlay: isWindows
|
||||||
|
? {
|
||||||
|
color: appTheme === 'dark' ? '#3f3f3f' : '#fff',
|
||||||
|
symbolColor: appTheme === 'dark' ? '#fff' : '#000',
|
||||||
|
height: 30
|
||||||
|
}
|
||||||
|
: false,
|
||||||
trafficLightPosition: isMacOS ? { x: 10, y: 8 } : undefined,
|
trafficLightPosition: isMacOS ? { x: 10, y: 8 } : undefined,
|
||||||
backgroundColor: '#1d1d1d'
|
backgroundColor: '#1d1d1d'
|
||||||
});
|
});
|
||||||
|
@ -73,10 +83,24 @@ else {
|
||||||
// Initialize ipcHandlers
|
// Initialize ipcHandlers
|
||||||
ipcHandlers();
|
ipcHandlers();
|
||||||
|
|
||||||
|
ipcMain.on('refresh-theme-settings', () => {
|
||||||
|
const appTheme = persistentStore.get('application_theme');
|
||||||
|
if(isWindows){
|
||||||
|
mainWindow.setTitleBarOverlay({
|
||||||
|
color: appTheme === 'dark' ? '#3f3f3f' : '#fff',
|
||||||
|
symbolColor: appTheme === 'dark' ? '#fff' : '#000'
|
||||||
|
});
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
ipcMain.on('change-window-title', (event, title: string) => {
|
||||||
|
if (mainWindow) mainWindow.setTitle(title);
|
||||||
|
});
|
||||||
|
|
||||||
// quit application when all windows are closed
|
// quit application when all windows are closed
|
||||||
app.on('window-all-closed', () => {
|
app.on('window-all-closed', () => {
|
||||||
// on macOS it is common for applications to stay open until the user explicitly quits
|
// on macOS it is common for applications to stay open until the user explicitly quits
|
||||||
if (isMacOS) app.quit();
|
if (!isMacOS) app.quit();
|
||||||
});
|
});
|
||||||
|
|
||||||
app.on('activate', async () => {
|
app.on('activate', async () => {
|
||||||
|
|
|
@ -222,8 +222,16 @@ export default defineComponent({
|
||||||
hightlightedIndex.value = 0;
|
hightlightedIndex.value = 0;
|
||||||
});
|
});
|
||||||
|
|
||||||
|
watch(() => props.modelValue, (val) => {
|
||||||
|
internalValue.value = val;
|
||||||
|
});
|
||||||
|
|
||||||
|
watch(() => props.value, (val) => {
|
||||||
|
internalValue.value = val;
|
||||||
|
});
|
||||||
|
|
||||||
const currentOptionLabel = computed(() =>
|
const currentOptionLabel = computed(() =>
|
||||||
flattenOptions.value.find(d => d.value === props.modelValue)?.label
|
flattenOptions.value.find(d => d.value === internalValue.value)?.label
|
||||||
);
|
);
|
||||||
|
|
||||||
const select = (opt) => {
|
const select = (opt) => {
|
||||||
|
|
|
@ -77,6 +77,7 @@ const { showSettingModal, showScratchpad } = applicationStore;
|
||||||
const { getConnectionName, updateConnections } = connectionsStore;
|
const { getConnectionName, updateConnections } = connectionsStore;
|
||||||
const { getWorkspace, selectWorkspace } = workspacesStore;
|
const { getWorkspace, selectWorkspace } = workspacesStore;
|
||||||
|
|
||||||
|
const isLinux = process.platform === 'linux';
|
||||||
const isContext: Ref<boolean> = ref(false);
|
const isContext: Ref<boolean> = ref(false);
|
||||||
const isDragging: Ref<boolean> = ref(false);
|
const isDragging: Ref<boolean> = ref(false);
|
||||||
const contextEvent: Ref<MouseEvent> = ref(null);
|
const contextEvent: Ref<MouseEvent> = ref(null);
|
||||||
|
@ -101,7 +102,9 @@ const contextMenu = (event: MouseEvent, connection: ConnectionParams) => {
|
||||||
|
|
||||||
const tooltipPosition = (e: Event) => {
|
const tooltipPosition = (e: Event) => {
|
||||||
const el = e.target ? e.target : e;
|
const el = e.target ? e.target : e;
|
||||||
const fromTop = window.scrollY + (el as HTMLElement).getBoundingClientRect().top - ((el as HTMLElement).offsetHeight / 4);
|
const fromTop = isLinux
|
||||||
|
? window.scrollY + (el as HTMLElement).getBoundingClientRect().top + ((el as HTMLElement).offsetHeight / 4)
|
||||||
|
: window.scrollY + (el as HTMLElement).getBoundingClientRect().top - ((el as HTMLElement).offsetHeight / 4);
|
||||||
(el as HTMLElement).querySelector<HTMLElement>('.ex-tooltip-content').style.top = `${fromTop}px`;
|
(el as HTMLElement).querySelector<HTMLElement>('.ex-tooltip-content').style.top = `${fromTop}px`;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,9 @@
|
||||||
<template>
|
<template>
|
||||||
<div id="titlebar" @dblclick="toggleFullScreen">
|
<div
|
||||||
|
v-if="!isLinux"
|
||||||
|
id="titlebar"
|
||||||
|
@dblclick="toggleFullScreen"
|
||||||
|
>
|
||||||
<div class="titlebar-resizer" />
|
<div class="titlebar-resizer" />
|
||||||
<div class="titlebar-elements">
|
<div class="titlebar-elements">
|
||||||
<img
|
<img
|
||||||
|
@ -26,28 +30,7 @@
|
||||||
>
|
>
|
||||||
<i class="mdi mdi-24px mdi-refresh" />
|
<i class="mdi mdi-24px mdi-refresh" />
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div v-if="isWindows" style="width: 140px;" />
|
||||||
v-if="!isMacOS"
|
|
||||||
class="titlebar-element"
|
|
||||||
@click="minimizeApp"
|
|
||||||
>
|
|
||||||
<i class="mdi mdi-24px mdi-minus" />
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
v-if="!isMacOS"
|
|
||||||
class="titlebar-element"
|
|
||||||
@click="toggleFullScreen"
|
|
||||||
>
|
|
||||||
<i v-if="isMaximized" class="mdi mdi-24px mdi-fullscreen-exit" />
|
|
||||||
<i v-else class="mdi mdi-24px mdi-fullscreen" />
|
|
||||||
</div>
|
|
||||||
<div
|
|
||||||
v-if="!isMacOS"
|
|
||||||
class="titlebar-element close-button"
|
|
||||||
@click="closeApp"
|
|
||||||
>
|
|
||||||
<i class="mdi mdi-24px mdi-close" />
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
|
@ -55,7 +38,6 @@
|
||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
import { computed, onUnmounted, ref } from 'vue';
|
import { computed, onUnmounted, ref } from 'vue';
|
||||||
import { storeToRefs } from 'pinia';
|
import { storeToRefs } from 'pinia';
|
||||||
import { ipcRenderer } from 'electron';
|
|
||||||
import { getCurrentWindow } from '@electron/remote';
|
import { getCurrentWindow } from '@electron/remote';
|
||||||
import { useConnectionsStore } from '@/stores/connections';
|
import { useConnectionsStore } from '@/stores/connections';
|
||||||
import { useWorkspacesStore } from '@/stores/workspaces';
|
import { useWorkspacesStore } from '@/stores/workspaces';
|
||||||
|
@ -74,7 +56,9 @@ const appIcon = require('@/images/logo.svg');
|
||||||
const w = ref(getCurrentWindow());
|
const w = ref(getCurrentWindow());
|
||||||
const isMaximized = ref(getCurrentWindow().isMaximized());
|
const isMaximized = ref(getCurrentWindow().isMaximized());
|
||||||
const isDevelopment = ref(process.env.NODE_ENV === 'development');
|
const isDevelopment = ref(process.env.NODE_ENV === 'development');
|
||||||
const isMacOS = ref(process.platform === 'darwin');
|
const isMacOS = process.platform === 'darwin';
|
||||||
|
const isWindows = process.platform === 'win32';
|
||||||
|
const isLinux = process.platform === 'linux';
|
||||||
|
|
||||||
const windowTitle = computed(() => {
|
const windowTitle = computed(() => {
|
||||||
if (!selectedWorkspace.value) return '';
|
if (!selectedWorkspace.value) return '';
|
||||||
|
@ -87,14 +71,6 @@ const windowTitle = computed(() => {
|
||||||
return [connectionName, ...breadcrumbs].join(' • ');
|
return [connectionName, ...breadcrumbs].join(' • ');
|
||||||
});
|
});
|
||||||
|
|
||||||
const closeApp = () => {
|
|
||||||
ipcRenderer.send('close-app');
|
|
||||||
};
|
|
||||||
|
|
||||||
const minimizeApp = () => {
|
|
||||||
w.value.minimize();
|
|
||||||
};
|
|
||||||
|
|
||||||
const toggleFullScreen = () => {
|
const toggleFullScreen = () => {
|
||||||
if (isMaximized.value)
|
if (isMaximized.value)
|
||||||
w.value.unmaximize();
|
w.value.unmaximize();
|
||||||
|
@ -165,7 +141,7 @@ onUnmounted(() => {
|
||||||
height: $titlebar-height;
|
height: $titlebar-height;
|
||||||
line-height: 0;
|
line-height: 0;
|
||||||
padding: 0 0.7rem;
|
padding: 0 0.7rem;
|
||||||
opacity: 0.7;
|
opacity: 0.9;
|
||||||
transition: opacity 0.2s;
|
transition: opacity 0.2s;
|
||||||
-webkit-app-region: no-drag;
|
-webkit-app-region: no-drag;
|
||||||
|
|
||||||
|
|
|
@ -315,10 +315,9 @@
|
||||||
</template>
|
</template>
|
||||||
</Draggable>
|
</Draggable>
|
||||||
<WorkspaceEmptyState v-if="!workspace.tabs.length" @new-tab="addQueryTab" />
|
<WorkspaceEmptyState v-if="!workspace.tabs.length" @new-tab="addQueryTab" />
|
||||||
<template v-for="tab of workspace.tabs">
|
<template v-for="tab of workspace.tabs" :key="tab.uid">
|
||||||
<WorkspaceTabQuery
|
<WorkspaceTabQuery
|
||||||
v-if="tab.type==='query'"
|
v-if="tab.type ==='query'"
|
||||||
:key="tab.uid"
|
|
||||||
:tab-uid="tab.uid"
|
:tab-uid="tab.uid"
|
||||||
:tab="tab"
|
:tab="tab"
|
||||||
:is-selected="selectedTab === tab.uid"
|
:is-selected="selectedTab === tab.uid"
|
||||||
|
@ -326,7 +325,7 @@
|
||||||
/>
|
/>
|
||||||
<WorkspaceTabTable
|
<WorkspaceTabTable
|
||||||
v-else-if="['temp-data', 'data'].includes(tab.type)"
|
v-else-if="['temp-data', 'data'].includes(tab.type)"
|
||||||
:key="tab.uid+'_data'"
|
v-once
|
||||||
:tab-uid="tab.uid"
|
:tab-uid="tab.uid"
|
||||||
:connection="connection"
|
:connection="connection"
|
||||||
:is-selected="selectedTab === tab.uid"
|
:is-selected="selectedTab === tab.uid"
|
||||||
|
@ -336,7 +335,6 @@
|
||||||
/>
|
/>
|
||||||
<WorkspaceTabNewTable
|
<WorkspaceTabNewTable
|
||||||
v-else-if="tab.type === 'new-table'"
|
v-else-if="tab.type === 'new-table'"
|
||||||
:key="tab.uid+'_new-table'"
|
|
||||||
:tab-uid="tab.uid"
|
:tab-uid="tab.uid"
|
||||||
:tab="tab"
|
:tab="tab"
|
||||||
:connection="connection"
|
:connection="connection"
|
||||||
|
@ -345,7 +343,6 @@
|
||||||
/>
|
/>
|
||||||
<WorkspaceTabPropsTable
|
<WorkspaceTabPropsTable
|
||||||
v-else-if="tab.type === 'table-props'"
|
v-else-if="tab.type === 'table-props'"
|
||||||
:key="tab.uid+'_table-props'"
|
|
||||||
:tab-uid="tab.uid"
|
:tab-uid="tab.uid"
|
||||||
:connection="connection"
|
:connection="connection"
|
||||||
:is-selected="selectedTab === tab.uid"
|
:is-selected="selectedTab === tab.uid"
|
||||||
|
@ -354,7 +351,6 @@
|
||||||
/>
|
/>
|
||||||
<WorkspaceTabNewView
|
<WorkspaceTabNewView
|
||||||
v-else-if="tab.type === 'new-view'"
|
v-else-if="tab.type === 'new-view'"
|
||||||
:key="tab.uid+'_new-view'"
|
|
||||||
:tab-uid="tab.uid"
|
:tab-uid="tab.uid"
|
||||||
:tab="tab"
|
:tab="tab"
|
||||||
:connection="connection"
|
:connection="connection"
|
||||||
|
@ -363,7 +359,6 @@
|
||||||
/>
|
/>
|
||||||
<WorkspaceTabPropsView
|
<WorkspaceTabPropsView
|
||||||
v-else-if="tab.type === 'view-props'"
|
v-else-if="tab.type === 'view-props'"
|
||||||
:key="tab.uid+'_view-props'"
|
|
||||||
:tab-uid="tab.uid"
|
:tab-uid="tab.uid"
|
||||||
:is-selected="selectedTab === tab.uid"
|
:is-selected="selectedTab === tab.uid"
|
||||||
:connection="connection"
|
:connection="connection"
|
||||||
|
@ -372,7 +367,6 @@
|
||||||
/>
|
/>
|
||||||
<WorkspaceTabNewTrigger
|
<WorkspaceTabNewTrigger
|
||||||
v-else-if="tab.type === 'new-trigger'"
|
v-else-if="tab.type === 'new-trigger'"
|
||||||
:key="tab.uid+'_new-trigger'"
|
|
||||||
:tab-uid="tab.uid"
|
:tab-uid="tab.uid"
|
||||||
:tab="tab"
|
:tab="tab"
|
||||||
:connection="connection"
|
:connection="connection"
|
||||||
|
@ -382,7 +376,6 @@
|
||||||
/>
|
/>
|
||||||
<WorkspaceTabPropsTrigger
|
<WorkspaceTabPropsTrigger
|
||||||
v-else-if="['temp-trigger-props', 'trigger-props'].includes(tab.type)"
|
v-else-if="['temp-trigger-props', 'trigger-props'].includes(tab.type)"
|
||||||
:key="tab.uid+'_trigger-props'"
|
|
||||||
:tab-uid="tab.uid"
|
:tab-uid="tab.uid"
|
||||||
:connection="connection"
|
:connection="connection"
|
||||||
:is-selected="selectedTab === tab.uid"
|
:is-selected="selectedTab === tab.uid"
|
||||||
|
@ -391,7 +384,6 @@
|
||||||
/>
|
/>
|
||||||
<WorkspaceTabNewTriggerFunction
|
<WorkspaceTabNewTriggerFunction
|
||||||
v-else-if="tab.type === 'new-trigger-function'"
|
v-else-if="tab.type === 'new-trigger-function'"
|
||||||
:key="tab.uid+'_new-trigger-function'"
|
|
||||||
:tab-uid="tab.uid"
|
:tab-uid="tab.uid"
|
||||||
:tab="tab"
|
:tab="tab"
|
||||||
:connection="connection"
|
:connection="connection"
|
||||||
|
@ -401,7 +393,6 @@
|
||||||
/>
|
/>
|
||||||
<WorkspaceTabPropsTriggerFunction
|
<WorkspaceTabPropsTriggerFunction
|
||||||
v-else-if="['temp-trigger-function-props', 'trigger-function-props'].includes(tab.type)"
|
v-else-if="['temp-trigger-function-props', 'trigger-function-props'].includes(tab.type)"
|
||||||
:key="tab.uid+'_trigger-function-props'"
|
|
||||||
:tab-uid="tab.uid"
|
:tab-uid="tab.uid"
|
||||||
:connection="connection"
|
:connection="connection"
|
||||||
:is-selected="selectedTab === tab.uid"
|
:is-selected="selectedTab === tab.uid"
|
||||||
|
@ -410,7 +401,6 @@
|
||||||
/>
|
/>
|
||||||
<WorkspaceTabNewRoutine
|
<WorkspaceTabNewRoutine
|
||||||
v-else-if="tab.type === 'new-routine'"
|
v-else-if="tab.type === 'new-routine'"
|
||||||
:key="tab.uid+'_new-routine'"
|
|
||||||
:tab-uid="tab.uid"
|
:tab-uid="tab.uid"
|
||||||
:tab="tab"
|
:tab="tab"
|
||||||
:connection="connection"
|
:connection="connection"
|
||||||
|
@ -420,7 +410,6 @@
|
||||||
/>
|
/>
|
||||||
<WorkspaceTabPropsRoutine
|
<WorkspaceTabPropsRoutine
|
||||||
v-else-if="['temp-routine-props', 'routine-props'].includes(tab.type)"
|
v-else-if="['temp-routine-props', 'routine-props'].includes(tab.type)"
|
||||||
:key="tab.uid+'_routine-props'"
|
|
||||||
:tab-uid="tab.uid"
|
:tab-uid="tab.uid"
|
||||||
:connection="connection"
|
:connection="connection"
|
||||||
:is-selected="selectedTab === tab.uid"
|
:is-selected="selectedTab === tab.uid"
|
||||||
|
@ -429,7 +418,6 @@
|
||||||
/>
|
/>
|
||||||
<WorkspaceTabNewFunction
|
<WorkspaceTabNewFunction
|
||||||
v-else-if="tab.type === 'new-function'"
|
v-else-if="tab.type === 'new-function'"
|
||||||
:key="tab.uid+'_new-function'"
|
|
||||||
:tab-uid="tab.uid"
|
:tab-uid="tab.uid"
|
||||||
:tab="tab"
|
:tab="tab"
|
||||||
:connection="connection"
|
:connection="connection"
|
||||||
|
@ -439,7 +427,6 @@
|
||||||
/>
|
/>
|
||||||
<WorkspaceTabPropsFunction
|
<WorkspaceTabPropsFunction
|
||||||
v-else-if="['temp-function-props', 'function-props'].includes(tab.type)"
|
v-else-if="['temp-function-props', 'function-props'].includes(tab.type)"
|
||||||
:key="tab.uid+'_function-props'"
|
|
||||||
:tab-uid="tab.uid"
|
:tab-uid="tab.uid"
|
||||||
:connection="connection"
|
:connection="connection"
|
||||||
:is-selected="selectedTab === tab.uid"
|
:is-selected="selectedTab === tab.uid"
|
||||||
|
@ -448,7 +435,6 @@
|
||||||
/>
|
/>
|
||||||
<WorkspaceTabNewScheduler
|
<WorkspaceTabNewScheduler
|
||||||
v-else-if="tab.type === 'new-scheduler'"
|
v-else-if="tab.type === 'new-scheduler'"
|
||||||
:key="tab.uid+'_new-scheduler'"
|
|
||||||
:tab-uid="tab.uid"
|
:tab-uid="tab.uid"
|
||||||
:tab="tab"
|
:tab="tab"
|
||||||
:connection="connection"
|
:connection="connection"
|
||||||
|
@ -458,7 +444,6 @@
|
||||||
/>
|
/>
|
||||||
<WorkspaceTabPropsScheduler
|
<WorkspaceTabPropsScheduler
|
||||||
v-else-if="['temp-scheduler-props', 'scheduler-props'].includes(tab.type)"
|
v-else-if="['temp-scheduler-props', 'scheduler-props'].includes(tab.type)"
|
||||||
:key="tab.uid+'_scheduler-props'"
|
|
||||||
:tab-uid="tab.uid"
|
:tab-uid="tab.uid"
|
||||||
:connection="connection"
|
:connection="connection"
|
||||||
:is-selected="selectedTab === tab.uid"
|
:is-selected="selectedTab === tab.uid"
|
||||||
|
|
|
@ -516,9 +516,9 @@ const continueTest = async (credentials: { user: string; password: string }) =>
|
||||||
isTesting.value = false;
|
isTesting.value = false;
|
||||||
};
|
};
|
||||||
|
|
||||||
const saveConnection = () => {
|
const saveConnection = async () => {
|
||||||
|
await addConnection(connection.value);
|
||||||
selectWorkspace(connection.value.uid);
|
selectWorkspace(connection.value.uid);
|
||||||
return addConnection(connection.value);
|
|
||||||
};
|
};
|
||||||
|
|
||||||
const closeAsking = () => {
|
const closeAsking = () => {
|
||||||
|
|
|
@ -438,15 +438,12 @@ export default {
|
||||||
|
|
||||||
// Fields Changes
|
// Fields Changes
|
||||||
const changes = [];
|
const changes = [];
|
||||||
this.originalFields.forEach((originalField, oI) => {
|
this.localFields.forEach((field, i) => {
|
||||||
const lI = this.localFields.findIndex(localField => localField._antares_id === originalField._antares_id);
|
const originalField = this.originalFields.find(oField => oField._antares_id === field._antares_id);
|
||||||
const originalSibling = oI > 0 ? this.originalFields[oI - 1]._antares_id : false;
|
const after = i > 0 ? this.localFields[i - 1].name : false;
|
||||||
const localSibling = lI > 0 ? this.localFields[lI - 1]._antares_id : false;
|
|
||||||
const after = lI > 0 ? this.localFields[lI - 1].name : false;
|
|
||||||
const orgName = originalField.name;
|
const orgName = originalField.name;
|
||||||
|
|
||||||
if (JSON.stringify(originalField) !== JSON.stringify(this.localFields[lI]) || originalSibling !== localSibling)
|
changes.push({ ...field, after, orgName });
|
||||||
if (this.localFields[lI]) changes.push({ ...this.localFields[lI], after, orgName });
|
|
||||||
});
|
});
|
||||||
|
|
||||||
// OPTIONS
|
// OPTIONS
|
||||||
|
|
|
@ -5,7 +5,6 @@
|
||||||
tabindex="0"
|
tabindex="0"
|
||||||
:style="{'height': resultsSize+'px'}"
|
:style="{'height': resultsSize+'px'}"
|
||||||
@keyup.delete="showDeleteConfirmModal"
|
@keyup.delete="showDeleteConfirmModal"
|
||||||
@keydown.ctrl.a="selectAllRows($event)"
|
|
||||||
@keydown.esc="deselectRows"
|
@keydown.esc="deselectRows"
|
||||||
>
|
>
|
||||||
<TableContext
|
<TableContext
|
||||||
|
@ -78,7 +77,11 @@
|
||||||
:key-usage="keyUsage"
|
:key-usage="keyUsage"
|
||||||
:element-type="elementType"
|
:element-type="elementType"
|
||||||
:class="{'selected': selectedRows.includes(row._antares_id)}"
|
:class="{'selected': selectedRows.includes(row._antares_id)}"
|
||||||
@select-row="selectRow($event, row._antares_id)"
|
:selected="selectedRows.includes(row._antares_id)"
|
||||||
|
:selected-cell="selectedRows.length === 1 && selectedRows.includes(row._antares_id) ? selectedField : null"
|
||||||
|
@start-editing="isEditingRow = true"
|
||||||
|
@stop-editing="isEditingRow = false"
|
||||||
|
@select-row="selectRow"
|
||||||
@update-field="updateField($event, row)"
|
@update-field="updateField($event, row)"
|
||||||
@contextmenu="contextMenu"
|
@contextmenu="contextMenu"
|
||||||
/>
|
/>
|
||||||
|
@ -162,7 +165,9 @@ export default {
|
||||||
currentSortDir: 'asc',
|
currentSortDir: 'asc',
|
||||||
resultsetIndex: 0,
|
resultsetIndex: 0,
|
||||||
scrollElement: null,
|
scrollElement: null,
|
||||||
rowHeight: 23
|
rowHeight: 23,
|
||||||
|
selectedField: null,
|
||||||
|
isEditingRow: false
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
computed: {
|
computed: {
|
||||||
|
@ -268,9 +273,11 @@ export default {
|
||||||
},
|
},
|
||||||
mounted () {
|
mounted () {
|
||||||
window.addEventListener('resize', this.resizeResults);
|
window.addEventListener('resize', this.resizeResults);
|
||||||
|
window.addEventListener('keydown', this.onKey);
|
||||||
},
|
},
|
||||||
unmounted () {
|
unmounted () {
|
||||||
window.removeEventListener('resize', this.resizeResults);
|
window.removeEventListener('resize', this.resizeResults);
|
||||||
|
window.removeEventListener('keydown', this.onKey);
|
||||||
},
|
},
|
||||||
methods: {
|
methods: {
|
||||||
fieldType (cKey) {
|
fieldType (cKey) {
|
||||||
|
@ -447,20 +454,23 @@ export default {
|
||||||
return row;
|
return row;
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
selectRow (event, row) {
|
selectRow (event, row, field) {
|
||||||
if (event.ctrlKey) {
|
this.selectedField = field;
|
||||||
if (this.selectedRows.includes(row))
|
const selectedRowId = row._antares_id;
|
||||||
this.selectedRows = this.selectedRows.filter(el => el !== row);
|
|
||||||
|
if (event.ctrlKey || event.metaKey) {
|
||||||
|
if (this.selectedRows.includes(selectedRowId))
|
||||||
|
this.selectedRows = this.selectedRows.filter(el => el !== selectedRowId);
|
||||||
else
|
else
|
||||||
this.selectedRows.push(row);
|
this.selectedRows.push(selectedRowId);
|
||||||
}
|
}
|
||||||
else if (event.shiftKey) {
|
else if (event.shiftKey) {
|
||||||
if (!this.selectedRows.length)
|
if (!this.selectedRows.length)
|
||||||
this.selectedRows.push(row);
|
this.selectedRows.push(selectedRowId);
|
||||||
else {
|
else {
|
||||||
const lastID = this.selectedRows.slice(-1)[0];
|
const lastID = this.selectedRows.slice(-1)[0];
|
||||||
const lastIndex = this.sortedResults.findIndex(el => el._antares_id === lastID);
|
const lastIndex = this.sortedResults.findIndex(el => el._antares_id === lastID);
|
||||||
const clickedIndex = this.sortedResults.findIndex(el => el._antares_id === row);
|
const clickedIndex = this.sortedResults.findIndex(el => el._antares_id === selectedRowId);
|
||||||
if (lastIndex > clickedIndex) {
|
if (lastIndex > clickedIndex) {
|
||||||
for (let i = clickedIndex; i < lastIndex; i++)
|
for (let i = clickedIndex; i < lastIndex; i++)
|
||||||
this.selectedRows.push(this.sortedResults[i]._antares_id);
|
this.selectedRows.push(this.sortedResults[i]._antares_id);
|
||||||
|
@ -472,18 +482,20 @@ export default {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
this.selectedRows = [row];
|
this.selectedRows = [selectedRowId];
|
||||||
},
|
},
|
||||||
selectAllRows (e) {
|
selectAllRows (e) {
|
||||||
if (e.target.classList.contains('editable-field')) return;
|
if (e.target.classList.contains('editable-field')) return;
|
||||||
|
|
||||||
|
this.selectedField = 0;
|
||||||
this.selectedRows = this.localResults.reduce((acc, curr) => {
|
this.selectedRows = this.localResults.reduce((acc, curr) => {
|
||||||
acc.push(curr._antares_id);
|
acc.push(curr._antares_id);
|
||||||
return acc;
|
return acc;
|
||||||
}, []);
|
}, []);
|
||||||
},
|
},
|
||||||
deselectRows () {
|
deselectRows () {
|
||||||
this.selectedRows = [];
|
if (!this.isEditingRow)
|
||||||
|
this.selectedRows = [];
|
||||||
},
|
},
|
||||||
contextMenu (event, cell) {
|
contextMenu (event, cell) {
|
||||||
if (event.target.localName === 'input') return;
|
if (event.target.localName === 'input') return;
|
||||||
|
@ -536,6 +548,113 @@ export default {
|
||||||
content: rows,
|
content: rows,
|
||||||
filename
|
filename
|
||||||
});
|
});
|
||||||
|
},
|
||||||
|
onKey (e) {
|
||||||
|
if (!this.isSelected)
|
||||||
|
return;
|
||||||
|
|
||||||
|
if (this.isEditingRow)
|
||||||
|
return;
|
||||||
|
|
||||||
|
if ((e.ctrlKey || e.metaKey) && e.code === 'KeyA' && !e.altKey)
|
||||||
|
this.selectAllRows(e);
|
||||||
|
|
||||||
|
// row naviation stuff
|
||||||
|
if ((e.code.includes('Arrow') || e.code === 'Tab') && this.sortedResults.length > 0 && !e.altKey) {
|
||||||
|
e.preventDefault();
|
||||||
|
|
||||||
|
const aviableFields= Object.keys(this.sortedResults[0]).slice(0, -1); // removes _antares_id
|
||||||
|
|
||||||
|
if (!this.selectedField)
|
||||||
|
this.selectedField = aviableFields[0];
|
||||||
|
|
||||||
|
const selectedId = this.selectedRows[0];
|
||||||
|
const selectedIndex = this.sortedResults.findIndex(row => row._antares_id === selectedId);
|
||||||
|
const selectedFieldIndex = aviableFields.findIndex(field => field === this.selectedField);
|
||||||
|
let nextIndex = 0;
|
||||||
|
let nextFieldIndex = 0;
|
||||||
|
|
||||||
|
if (selectedIndex > -1) {
|
||||||
|
switch (e.code) {
|
||||||
|
case 'ArrowDown':
|
||||||
|
nextIndex = selectedIndex + 1;
|
||||||
|
nextFieldIndex = selectedFieldIndex;
|
||||||
|
|
||||||
|
if (nextIndex > this.sortedResults.length -1)
|
||||||
|
nextIndex = this.sortedResults.length -1;
|
||||||
|
|
||||||
|
break;
|
||||||
|
case 'ArrowUp':
|
||||||
|
nextIndex = selectedIndex - 1;
|
||||||
|
nextFieldIndex = selectedFieldIndex;
|
||||||
|
|
||||||
|
if (nextIndex < 0)
|
||||||
|
nextIndex = 0;
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 'ArrowRight':
|
||||||
|
nextIndex = selectedIndex;
|
||||||
|
nextFieldIndex = selectedFieldIndex + 1;
|
||||||
|
|
||||||
|
if (nextFieldIndex > aviableFields.length -1)
|
||||||
|
nextFieldIndex = 0;
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 'ArrowLeft':
|
||||||
|
nextIndex = selectedIndex;
|
||||||
|
nextFieldIndex = selectedFieldIndex - 1;
|
||||||
|
|
||||||
|
if (nextFieldIndex < 0)
|
||||||
|
nextFieldIndex = aviableFields.length -1;
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 'Tab':
|
||||||
|
nextIndex = selectedIndex;
|
||||||
|
if (e.shiftKey) {
|
||||||
|
nextFieldIndex = selectedFieldIndex - 1;
|
||||||
|
if (nextFieldIndex < 0)
|
||||||
|
nextFieldIndex = aviableFields.length -1;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
nextFieldIndex = selectedFieldIndex + 1;
|
||||||
|
if (nextFieldIndex > aviableFields.length -1)
|
||||||
|
nextFieldIndex = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (this.sortedResults[nextIndex] && nextIndex !== selectedIndex) {
|
||||||
|
this.selectedRows = [this.sortedResults[nextIndex]._antares_id];
|
||||||
|
this.$nextTick(() => this.scrollToCell(this.scrollElement.querySelector('.td.selected')));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (aviableFields[nextFieldIndex] && nextFieldIndex !== selectedFieldIndex) {
|
||||||
|
this.selectedField = aviableFields[nextFieldIndex];
|
||||||
|
this.$nextTick(() => this.scrollToCell(this.scrollElement.querySelector('.td.selected')));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
scrollToCell (el) {
|
||||||
|
if (!el) return;
|
||||||
|
const visYMin = this.scrollElement.scrollTop;
|
||||||
|
const visYMax = this.scrollElement.scrollTop + this.scrollElement.clientHeight - el.clientHeight;
|
||||||
|
const visXMin = this.scrollElement.scrollLeft;
|
||||||
|
const visXMax = this.scrollElement.scrollLeft + this.scrollElement.clientWidth - el.clientWidth;
|
||||||
|
|
||||||
|
if (el.offsetTop < visYMin)
|
||||||
|
this.scrollElement.scrollTop = el.offsetTop;
|
||||||
|
|
||||||
|
else if (el.offsetTop >= visYMax)
|
||||||
|
this.scrollElement.scrollTop = el.offsetTop - this.scrollElement.clientHeight + el.clientHeight;
|
||||||
|
|
||||||
|
if (el.offsetLeft < visXMin)
|
||||||
|
this.scrollElement.scrollLeft = el.offsetLeft;
|
||||||
|
|
||||||
|
else if (el.offsetLeft >= visXMax)
|
||||||
|
this.scrollElement.scrollLeft = el.offsetLeft - this.scrollElement.clientWidth + el.clientWidth;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
|
@ -2,14 +2,15 @@
|
||||||
<div
|
<div
|
||||||
class="tr"
|
class="tr"
|
||||||
:style="{height: itemHeight+'px'}"
|
:style="{height: itemHeight+'px'}"
|
||||||
@click="selectRow($event, row._antares_id)"
|
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
v-for="(col, cKey) in row"
|
v-for="(col, cKey) in row"
|
||||||
v-show="cKey !== '_antares_id'"
|
v-show="cKey !== '_antares_id'"
|
||||||
:key="cKey"
|
:key="cKey"
|
||||||
class="td p-0"
|
class="td p-0"
|
||||||
tabindex="0"
|
:class="{selected: selectedCell === cKey}"
|
||||||
|
@click="selectRow($event, cKey)"
|
||||||
|
|
||||||
@contextmenu.prevent="openContext($event, { id: row._antares_id, orgField: cKey })"
|
@contextmenu.prevent="openContext($event, { id: row._antares_id, orgField: cKey })"
|
||||||
>
|
>
|
||||||
<template v-if="cKey !== '_antares_id'">
|
<template v-if="cKey !== '_antares_id'">
|
||||||
|
@ -17,7 +18,7 @@
|
||||||
v-if="!isInlineEditor[cKey] && fields[cKey]"
|
v-if="!isInlineEditor[cKey] && fields[cKey]"
|
||||||
class="cell-content"
|
class="cell-content"
|
||||||
:class="`${isNull(col)} ${typeClass(fields[cKey].type)}`"
|
:class="`${isNull(col)} ${typeClass(fields[cKey].type)}`"
|
||||||
@dblclick="editON($event, col, cKey)"
|
@dblclick="editON(cKey)"
|
||||||
>{{ cutText(typeFormat(col, fields[cKey].type.toLowerCase(), fields[cKey].length)) }}</span>
|
>{{ cutText(typeFormat(col, fields[cKey].type.toLowerCase(), fields[cKey].length)) }}</span>
|
||||||
<ForeignKeySelect
|
<ForeignKeySelect
|
||||||
v-else-if="isForeignKey(cKey)"
|
v-else-if="isForeignKey(cKey)"
|
||||||
|
@ -105,7 +106,7 @@
|
||||||
<div class="mr-4">
|
<div class="mr-4">
|
||||||
<b>{{ $t('word.size') }}</b>: {{ editingContent ? editingContent.length : 0 }}
|
<b>{{ $t('word.size') }}</b>: {{ editingContent ? editingContent.length : 0 }}
|
||||||
</div>
|
</div>
|
||||||
<div>
|
<div v-if="editingType">
|
||||||
<b>{{ $t('word.type') }}</b>: {{ editingType.toUpperCase() }}
|
<b>{{ $t('word.type') }}</b>: {{ editingType.toUpperCase() }}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
@ -170,7 +171,9 @@
|
||||||
<b>{{ $t('word.size') }}</b>: {{ formatBytes(editingContent.length) }}<br>
|
<b>{{ $t('word.size') }}</b>: {{ formatBytes(editingContent.length) }}<br>
|
||||||
<b>{{ $t('word.mimeType') }}</b>: {{ contentInfo.mime }}
|
<b>{{ $t('word.mimeType') }}</b>: {{ contentInfo.mime }}
|
||||||
</div>
|
</div>
|
||||||
<div><b>{{ $t('word.type') }}</b>: {{ editingType.toUpperCase() }}</div>
|
<div v-if="editingType">
|
||||||
|
<b>{{ $t('word.type') }}</b>: {{ editingType.toUpperCase() }}
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="mt-3">
|
<div class="mt-3">
|
||||||
<label>{{ $t('message.uploadFile') }}</label>
|
<label>{{ $t('message.uploadFile') }}</label>
|
||||||
|
@ -230,9 +233,11 @@ export default {
|
||||||
fields: Object,
|
fields: Object,
|
||||||
keyUsage: Array,
|
keyUsage: Array,
|
||||||
itemHeight: Number,
|
itemHeight: Number,
|
||||||
elementType: { type: String, default: 'table' }
|
elementType: { type: String, default: 'table' },
|
||||||
|
selected: { type: Boolean, default: false },
|
||||||
|
selectedCell: { type: String, default: null }
|
||||||
},
|
},
|
||||||
emits: ['update-field', 'select-row', 'contextmenu'],
|
emits: ['update-field', 'select-row', 'contextmenu', 'start-editing', 'stop-editing'],
|
||||||
data () {
|
data () {
|
||||||
return {
|
return {
|
||||||
isInlineEditor: {},
|
isInlineEditor: {},
|
||||||
|
@ -336,6 +341,9 @@ export default {
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
},
|
},
|
||||||
|
isBaseSelectField () {
|
||||||
|
return this.isForeignKey(this.editingField) || this.inputProps.type === 'boolean' || this.enumArray;
|
||||||
|
},
|
||||||
enumArray () {
|
enumArray () {
|
||||||
if (this.fields[this.editingField] && this.fields[this.editingField].enumValues)
|
if (this.fields[this.editingField] && this.fields[this.editingField].enumValues)
|
||||||
return this.fields[this.editingField].enumValues.replaceAll('\'', '').split(',');
|
return this.fields[this.editingField].enumValues.replaceAll('\'', '').split(',');
|
||||||
|
@ -362,8 +370,21 @@ export default {
|
||||||
this.editorMode = this.availableLanguages.find(lang => lang.id === filteredLanguages[0].languageId).slug;
|
this.editorMode = this.availableLanguages.find(lang => lang.id === filteredLanguages[0].languageId).slug;
|
||||||
})();
|
})();
|
||||||
}
|
}
|
||||||
|
},
|
||||||
|
selected (isSelected) {
|
||||||
|
if (isSelected)
|
||||||
|
window.addEventListener('keydown', this.onKey);
|
||||||
|
|
||||||
|
else {
|
||||||
|
this.editOFF();
|
||||||
|
window.removeEventListener('keydown', this.onKey);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
beforeUnmount () {
|
||||||
|
if (this.selected)
|
||||||
|
window.removeEventListener('keydown', this.onKey);
|
||||||
|
},
|
||||||
methods: {
|
methods: {
|
||||||
isForeignKey (key) {
|
isForeignKey (key) {
|
||||||
if (key.includes('.'))
|
if (key.includes('.'))
|
||||||
|
@ -382,11 +403,10 @@ export default {
|
||||||
bufferToBase64 (val) {
|
bufferToBase64 (val) {
|
||||||
return bufferToBase64(val);
|
return bufferToBase64(val);
|
||||||
},
|
},
|
||||||
editON (event, content, field) {
|
editON (field) {
|
||||||
if (!this.isEditable || this.editingType === 'none') return;
|
if (!this.isEditable || this.editingType === 'none') return;
|
||||||
|
|
||||||
window.addEventListener('keydown', this.onKey);
|
const content = this.row[field];
|
||||||
|
|
||||||
const type = this.fields[field].type.toUpperCase();
|
const type = this.fields[field].type.toUpperCase();
|
||||||
this.originalContent = this.typeFormat(content, type, this.fields[field].length);
|
this.originalContent = this.typeFormat(content, type, this.fields[field].length);
|
||||||
this.editingType = type;
|
this.editingType = type;
|
||||||
|
@ -396,6 +416,7 @@ export default {
|
||||||
if ([...LONG_TEXT, ...ARRAY, ...TEXT_SEARCH].includes(type)) {
|
if ([...LONG_TEXT, ...ARRAY, ...TEXT_SEARCH].includes(type)) {
|
||||||
this.isTextareaEditor = true;
|
this.isTextareaEditor = true;
|
||||||
this.editingContent = this.typeFormat(content, type);
|
this.editingContent = this.typeFormat(content, type);
|
||||||
|
this.$emit('start-editing', field);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -405,6 +426,7 @@ export default {
|
||||||
this.isMapModal = true;
|
this.isMapModal = true;
|
||||||
this.editingContent = this.typeFormat(content, type);
|
this.editingContent = this.typeFormat(content, type);
|
||||||
}
|
}
|
||||||
|
this.$emit('start-editing', field);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -426,19 +448,21 @@ export default {
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
this.$emit('start-editing', field);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Inline editable fields
|
// Inline editable fields
|
||||||
this.editingContent = this.originalContent;
|
this.editingContent = this.originalContent;
|
||||||
this.$nextTick(() => { // Focus on input
|
|
||||||
event.target.blur();
|
|
||||||
|
|
||||||
this.$nextTick(() => document.querySelector('.editable-field').focus());
|
|
||||||
});
|
|
||||||
|
|
||||||
const obj = { [field]: true };
|
const obj = { [field]: true };
|
||||||
this.isInlineEditor = { ...this.isInlineEditor, ...obj };
|
this.isInlineEditor = { ...this.isInlineEditor, ...obj };
|
||||||
|
|
||||||
|
this.$nextTick(() => { // Focus on input
|
||||||
|
document.querySelector('.editable-field').focus();
|
||||||
|
});
|
||||||
|
|
||||||
|
this.$emit('start-editing', field);
|
||||||
},
|
},
|
||||||
editOFF () {
|
editOFF () {
|
||||||
if (!this.editingField) return;
|
if (!this.editingField) return;
|
||||||
|
@ -451,7 +475,13 @@ export default {
|
||||||
this.editingContent = this.editingContent.slice(0, -1);
|
this.editingContent = this.editingContent.slice(0, -1);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (this.editingContent === this.typeFormat(this.originalContent, this.editingType, this.editingLength)) return;// If not changed
|
// If not changed
|
||||||
|
if (this.editingContent === this.typeFormat(this.originalContent, this.editingType, this.editingLength)) {
|
||||||
|
this.editingType = null;
|
||||||
|
this.editingField = null;
|
||||||
|
this.$emit('stop-editing', this.editingField);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
content = this.editingContent;
|
content = this.editingContent;
|
||||||
}
|
}
|
||||||
|
@ -472,15 +502,17 @@ export default {
|
||||||
content
|
content
|
||||||
});
|
});
|
||||||
|
|
||||||
|
this.$emit('stop-editing', this.editingField);
|
||||||
|
|
||||||
this.editingType = null;
|
this.editingType = null;
|
||||||
this.editingField = null;
|
this.editingField = null;
|
||||||
window.removeEventListener('keydown', this.onKey);
|
|
||||||
},
|
},
|
||||||
hideEditorModal () {
|
hideEditorModal () {
|
||||||
this.isTextareaEditor = false;
|
this.isTextareaEditor = false;
|
||||||
this.isBlobEditor = false;
|
this.isBlobEditor = false;
|
||||||
this.isMapModal = false;
|
this.isMapModal = false;
|
||||||
this.isMultiSpatial = false;
|
this.isMultiSpatial = false;
|
||||||
|
this.$emit('stop-editing', this.editingField);
|
||||||
},
|
},
|
||||||
downloadFile () {
|
downloadFile () {
|
||||||
const downloadLink = document.createElement('a');
|
const downloadLink = document.createElement('a');
|
||||||
|
@ -508,8 +540,8 @@ export default {
|
||||||
};
|
};
|
||||||
this.willBeDeleted = true;
|
this.willBeDeleted = true;
|
||||||
},
|
},
|
||||||
selectRow (event, row) {
|
selectRow (event, field) {
|
||||||
this.$emit('select-row', event, row);
|
this.$emit('select-row', event, this.row, field);
|
||||||
},
|
},
|
||||||
getKeyUsage (keyName) {
|
getKeyUsage (keyName) {
|
||||||
if (keyName.includes('.'))
|
if (keyName.includes('.'))
|
||||||
|
@ -523,10 +555,17 @@ export default {
|
||||||
},
|
},
|
||||||
onKey (e) {
|
onKey (e) {
|
||||||
e.stopPropagation();
|
e.stopPropagation();
|
||||||
if (e.key === 'Escape') {
|
|
||||||
|
if (!this.editingField && e.key === 'Enter')
|
||||||
|
return this.editON(this.selectedCell);
|
||||||
|
|
||||||
|
if (this.editingField && e.key === 'Enter' && !this.isBaseSelectField)
|
||||||
|
return this.editOFF();
|
||||||
|
|
||||||
|
if (this.editingField && e.key === 'Escape') {
|
||||||
this.isInlineEditor[this.editingField] = false;
|
this.isInlineEditor[this.editingField] = false;
|
||||||
this.editingField = null;
|
this.editingField = null;
|
||||||
window.removeEventListener('keydown', this.onKey);
|
this.$emit('stop-editing', this.editingField);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
formatBytes,
|
formatBytes,
|
||||||
|
|
Binary file not shown.
After Width: | Height: | Size: 5.8 KiB |
|
@ -27,4 +27,14 @@ $titlebar-height: 1.5rem;
|
||||||
$settingbar-width: 3rem;
|
$settingbar-width: 3rem;
|
||||||
$explorebar-width: 14rem;
|
$explorebar-width: 14rem;
|
||||||
$footer-height: 1.5rem;
|
$footer-height: 1.5rem;
|
||||||
$excluding-size: $footer-height + $titlebar-height;
|
|
||||||
|
@function get-excluding-size(){
|
||||||
|
@if $platform == linux{
|
||||||
|
@return $footer-height;
|
||||||
|
}
|
||||||
|
@else {
|
||||||
|
@return $footer-height + $titlebar-height;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
$excluding-size: get-excluding-size();
|
||||||
|
|
|
@ -231,7 +231,8 @@
|
||||||
.td {
|
.td {
|
||||||
border-color: $body-bg-dark;
|
border-color: $body-bg-dark;
|
||||||
|
|
||||||
&:focus {
|
&:focus,
|
||||||
|
&.selected {
|
||||||
box-shadow: inset 0 0 0 2px darken($body-font-color-dark, 40%);
|
box-shadow: inset 0 0 0 2px darken($body-font-color-dark, 40%);
|
||||||
background-color: rgba($color: #000, $alpha: 0.3);
|
background-color: rgba($color: #000, $alpha: 0.3);
|
||||||
}
|
}
|
||||||
|
@ -362,7 +363,7 @@
|
||||||
.titlebar-element {
|
.titlebar-element {
|
||||||
&:hover {
|
&:hover {
|
||||||
opacity: 1;
|
opacity: 1;
|
||||||
background: rgba($color: #fff, $alpha: 0.2);
|
background: rgba($color: #fff, $alpha: 0.1);
|
||||||
}
|
}
|
||||||
|
|
||||||
&.close-button:hover {
|
&.close-button:hover {
|
||||||
|
|
|
@ -132,7 +132,7 @@
|
||||||
.titlebar-element {
|
.titlebar-element {
|
||||||
&:hover {
|
&:hover {
|
||||||
opacity: 1;
|
opacity: 1;
|
||||||
background: rgba($color: rgb(172, 172, 172), $alpha: 0.2);
|
background: rgba($color: rgb(172, 172, 172), $alpha: 0.3);
|
||||||
}
|
}
|
||||||
|
|
||||||
&.close-button:hover {
|
&.close-button:hover {
|
||||||
|
@ -252,7 +252,8 @@
|
||||||
.td {
|
.td {
|
||||||
border-color: $body-bg;
|
border-color: $body-bg;
|
||||||
|
|
||||||
&:focus {
|
&:focus,
|
||||||
|
&.selected {
|
||||||
box-shadow: inset 0 0 0 2px lighten($body-font-color, 10%);
|
box-shadow: inset 0 0 0 2px lighten($body-font-color, 10%);
|
||||||
background-color: $body-font-color-dark;
|
background-color: $body-font-color-dark;
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,4 +1,5 @@
|
||||||
import { defineStore } from 'pinia';
|
import { defineStore } from 'pinia';
|
||||||
|
import { ipcRenderer } from 'electron';
|
||||||
import i18n from '@/i18n';
|
import i18n from '@/i18n';
|
||||||
import * as Store from 'electron-store';
|
import * as Store from 'electron-store';
|
||||||
const persistentStore = new Store({ name: 'settings' });
|
const persistentStore = new Store({ name: 'settings' });
|
||||||
|
@ -57,6 +58,7 @@ export const useSettingsStore = defineStore('settings', {
|
||||||
changeApplicationTheme (theme: string) {
|
changeApplicationTheme (theme: string) {
|
||||||
this.applicationTheme = theme;
|
this.applicationTheme = theme;
|
||||||
persistentStore.set('application_theme', this.applicationTheme);
|
persistentStore.set('application_theme', this.applicationTheme);
|
||||||
|
ipcRenderer.send('refresh-theme-settings');
|
||||||
},
|
},
|
||||||
changeEditorTheme (theme: string) {
|
changeEditorTheme (theme: string) {
|
||||||
this.editorTheme = theme;
|
this.editorTheme = theme;
|
||||||
|
|
|
@ -197,13 +197,14 @@ export const useWorkspacesStore = defineStore('workspaces', {
|
||||||
|
|
||||||
// Check if Maria or MySQL
|
// Check if Maria or MySQL
|
||||||
const isMySQL = version.name.includes('MySQL');
|
const isMySQL = version.name.includes('MySQL');
|
||||||
|
const isMaria = version.name.includes('Maria');
|
||||||
|
|
||||||
if (isMySQL && connection.client !== 'mysql') {
|
if (isMySQL && connection.client !== 'mysql') {
|
||||||
const connProxy = Object.assign({}, connection);
|
const connProxy = Object.assign({}, connection);
|
||||||
connProxy.client = 'mysql';
|
connProxy.client = 'mysql';
|
||||||
connectionsStore.editConnection(connProxy);
|
connectionsStore.editConnection(connProxy);
|
||||||
}
|
}
|
||||||
else if (!isMySQL && connection.client === 'mysql') {
|
else if (isMaria && connection.client === 'mysql') {
|
||||||
const connProxy = Object.assign({}, connection);
|
const connProxy = Object.assign({}, connection);
|
||||||
connProxy.client = 'maria';
|
connProxy.client = 'maria';
|
||||||
connectionsStore.editConnection(connProxy);
|
connectionsStore.editConnection(connProxy);
|
||||||
|
@ -687,6 +688,26 @@ export const useWorkspacesStore = defineStore('workspaces', {
|
||||||
: workspace
|
: workspace
|
||||||
);
|
);
|
||||||
},
|
},
|
||||||
|
selectNextTab ({ uid }: {uid: string }) {
|
||||||
|
const workspace = (this.workspaces as Workspace[]).find(workspace => workspace.uid === uid);
|
||||||
|
|
||||||
|
let newIndex = workspace.tabs.findIndex(tab => tab.selected || tab.uid === workspace.selectedTab) + 1;
|
||||||
|
|
||||||
|
if (newIndex > workspace.tabs.length -1)
|
||||||
|
newIndex = 0;
|
||||||
|
|
||||||
|
this.selectTab({ uid, tab: workspace.tabs[newIndex].uid });
|
||||||
|
},
|
||||||
|
selectPrevTab ({ uid }: {uid: string }) {
|
||||||
|
const workspace = (this.workspaces as Workspace[]).find(workspace => workspace.uid === uid);
|
||||||
|
|
||||||
|
let newIndex = workspace.tabs.findIndex(tab => tab.selected || tab.uid === workspace.selectedTab) - 1;
|
||||||
|
|
||||||
|
if (newIndex < 0)
|
||||||
|
newIndex = workspace.tabs.length -1;
|
||||||
|
|
||||||
|
this.selectTab({ uid, tab: workspace.tabs[newIndex].uid });
|
||||||
|
},
|
||||||
updateTabs ({ uid, tabs }: {uid: string; tabs: WorkspaceTab[]}) {
|
updateTabs ({ uid, tabs }: {uid: string; tabs: WorkspaceTab[]}) {
|
||||||
this.workspaces = (this.workspaces as Workspace[]).map(workspace => workspace.uid === uid
|
this.workspaces = (this.workspaces as Workspace[]).map(workspace => workspace.uid === uid
|
||||||
? { ...workspace, tabs }
|
? { ...workspace, tabs }
|
||||||
|
|
|
@ -21,6 +21,7 @@ test('launch app', async () => {
|
||||||
|
|
||||||
test('main window elements visibility', async () => {
|
test('main window elements visibility', async () => {
|
||||||
const visibleSelectors = [
|
const visibleSelectors = [
|
||||||
|
// '#titlebar',
|
||||||
'#window-content',
|
'#window-content',
|
||||||
'#settingbar',
|
'#settingbar',
|
||||||
'#footer'
|
'#footer'
|
||||||
|
|
|
@ -113,7 +113,9 @@ const config = {
|
||||||
{
|
{
|
||||||
loader: 'sass-loader',
|
loader: 'sass-loader',
|
||||||
options: {
|
options: {
|
||||||
additionalData: '@import "@/scss/_variables.scss";',
|
additionalData: `
|
||||||
|
$platform: ${process.platform};
|
||||||
|
@import "@/scss/_variables.scss";`,
|
||||||
sassOptions: { quietDeps: true }
|
sassOptions: { quietDeps: true }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue