mirror of
https://github.com/DeNNiiInc/dbgate.git
synced 2026-04-27 18:26:00 +00:00
connection modal
This commit is contained in:
1
.gitignore
vendored
1
.gitignore
vendored
@@ -24,3 +24,4 @@ yarn-debug.log*
|
|||||||
yarn-error.log*
|
yarn-error.log*
|
||||||
app/src/nativeModulesContent.js
|
app/src/nativeModulesContent.js
|
||||||
packages/api/src/nativeModulesContent.js
|
packages/api/src/nativeModulesContent.js
|
||||||
|
.VSCodeCounter
|
||||||
@@ -31,6 +31,9 @@ body {
|
|||||||
.icon-invisible {
|
.icon-invisible {
|
||||||
visibility: hidden;
|
visibility: hidden;
|
||||||
}
|
}
|
||||||
|
.flex {
|
||||||
|
display: flex;
|
||||||
|
}
|
||||||
|
|
||||||
/* html, body {
|
/* html, body {
|
||||||
position: relative;
|
position: relative;
|
||||||
|
|||||||
@@ -9,6 +9,7 @@
|
|||||||
import splitterDrag from './utility/splitterDrag';
|
import splitterDrag from './utility/splitterDrag';
|
||||||
import CurrentDropDownMenu from './modals/CurrentDropDownMenu.svelte';
|
import CurrentDropDownMenu from './modals/CurrentDropDownMenu.svelte';
|
||||||
import StatusBar from './widgets/StatusBar.svelte';
|
import StatusBar from './widgets/StatusBar.svelte';
|
||||||
|
import ModalLayer from './modals/ModalLayer.svelte';
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<div class={`${$currentTheme} root`}>
|
<div class={`${$currentTheme} root`}>
|
||||||
@@ -47,6 +48,7 @@
|
|||||||
</div>
|
</div>
|
||||||
{/if}
|
{/if}
|
||||||
<CurrentDropDownMenu />
|
<CurrentDropDownMenu />
|
||||||
|
<ModalLayer />
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<style>
|
<style>
|
||||||
|
|||||||
@@ -2,6 +2,8 @@ import { currentTheme, extensions, visibleToolbar } from '../stores';
|
|||||||
import registerCommand from './registerCommand';
|
import registerCommand from './registerCommand';
|
||||||
import { derived, get } from 'svelte/store';
|
import { derived, get } from 'svelte/store';
|
||||||
import { ThemeDefinition } from 'dbgate-types';
|
import { ThemeDefinition } from 'dbgate-types';
|
||||||
|
import ConnectionModal from '../modals/ConnectionModal.svelte';
|
||||||
|
import { showModal } from '../modals/modalTools';
|
||||||
|
|
||||||
function themeCommand(theme: ThemeDefinition) {
|
function themeCommand(theme: ThemeDefinition) {
|
||||||
return {
|
return {
|
||||||
@@ -39,3 +41,13 @@ registerCommand({
|
|||||||
onClick: () => visibleToolbar.set(0),
|
onClick: () => visibleToolbar.set(0),
|
||||||
enabledStore: derived(visibleToolbar, $visibleToolbar => $visibleToolbar),
|
enabledStore: derived(visibleToolbar, $visibleToolbar => $visibleToolbar),
|
||||||
});
|
});
|
||||||
|
|
||||||
|
registerCommand({
|
||||||
|
id: 'new.connection',
|
||||||
|
toolbar: true,
|
||||||
|
icon: 'icon connection',
|
||||||
|
toolbarName: 'Add connection',
|
||||||
|
category: 'New',
|
||||||
|
name: 'Connection',
|
||||||
|
onClick: () => showModal(ConnectionModal),
|
||||||
|
});
|
||||||
|
|||||||
5
packages/web/src/forms/FormButton.svelte
Normal file
5
packages/web/src/forms/FormButton.svelte
Normal file
@@ -0,0 +1,5 @@
|
|||||||
|
<script>
|
||||||
|
import FormStyledButton from '../widgets/FormStyledButton.svelte';
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<FormStyledButton type="button" on:click {...$$props} />
|
||||||
5
packages/web/src/forms/FormSubmit.svelte
Normal file
5
packages/web/src/forms/FormSubmit.svelte
Normal file
@@ -0,0 +1,5 @@
|
|||||||
|
<script>
|
||||||
|
import FormStyledButton from '../widgets/FormStyledButton.svelte';
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<FormStyledButton type="submit" on:click {...$$props} />
|
||||||
24
packages/web/src/modals/ConnectionModal.svelte
Normal file
24
packages/web/src/modals/ConnectionModal.svelte
Normal file
@@ -0,0 +1,24 @@
|
|||||||
|
<script lang="ts">
|
||||||
|
import registerCommand from '../commands/registerCommand';
|
||||||
|
import FormButton from '../forms/FormButton.svelte';
|
||||||
|
import FormSubmit from '../forms/FormSubmit.svelte';
|
||||||
|
|
||||||
|
import ModalBase from './ModalBase.svelte';
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<ModalBase {...$$restProps}>
|
||||||
|
<div slot="header">Add connection</div>
|
||||||
|
xxx
|
||||||
|
<div slot="footer" class="flex">
|
||||||
|
<div class="buttons">
|
||||||
|
<FormButton value="Test" />
|
||||||
|
<FormSubmit value="Save" />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</ModalBase>
|
||||||
|
|
||||||
|
<style>
|
||||||
|
.buttons {
|
||||||
|
flex-shrink: 0;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
93
packages/web/src/modals/ModalBase.svelte
Normal file
93
packages/web/src/modals/ModalBase.svelte
Normal file
@@ -0,0 +1,93 @@
|
|||||||
|
<script>
|
||||||
|
import FontIcon from '../icons/FontIcon.svelte';
|
||||||
|
import { closeModal } from './modalTools';
|
||||||
|
import clickOutside from '../utility/clickOutside';
|
||||||
|
|
||||||
|
export let fullScreen;
|
||||||
|
export let noPadding;
|
||||||
|
export let modalId;
|
||||||
|
|
||||||
|
function handleCloseModal() {
|
||||||
|
closeModal(modalId);
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<!-- The Modal -->
|
||||||
|
<div id="myModal" class="bglayer">
|
||||||
|
<!-- Modal content -->
|
||||||
|
<div class="window" class:fullScreen use:clickOutside on:clickOutside={handleCloseModal}>
|
||||||
|
<div class="header">
|
||||||
|
<div><slot name="header" /></div>
|
||||||
|
<div class="close" on:click={handleCloseModal}>
|
||||||
|
<FontIcon icon="icon close" />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="content" class:noPadding>
|
||||||
|
<slot />
|
||||||
|
</div>
|
||||||
|
<div class="footer">
|
||||||
|
<slot name="footer" />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<style>
|
||||||
|
.bglayer {
|
||||||
|
position: fixed;
|
||||||
|
z-index: 1;
|
||||||
|
left: 0;
|
||||||
|
top: 0;
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
overflow: auto;
|
||||||
|
background-color: rgb(0, 0, 0); /* Fallback color */
|
||||||
|
background-color: rgba(0, 0, 0, 0.4);
|
||||||
|
}
|
||||||
|
|
||||||
|
.window {
|
||||||
|
background-color: var(--theme-bg-0);
|
||||||
|
margin: auto;
|
||||||
|
margin-top: 15vh;
|
||||||
|
border: 1px solid var(--theme-border);
|
||||||
|
width: 50%;
|
||||||
|
overflow: auto;
|
||||||
|
outline: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
.window:not(.fullScreen) {
|
||||||
|
border-radius: 10px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.close {
|
||||||
|
font-size: 12pt;
|
||||||
|
padding: 5px 10px;
|
||||||
|
border-radius: 10px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.close:hover {
|
||||||
|
background-color: var(--theme-bg-2);
|
||||||
|
}
|
||||||
|
|
||||||
|
.header {
|
||||||
|
font-size: 15pt;
|
||||||
|
padding: 15px;
|
||||||
|
display: flex;
|
||||||
|
justify-content: space-between;
|
||||||
|
background-color: var(--theme-bg-modalheader);
|
||||||
|
}
|
||||||
|
|
||||||
|
.content {
|
||||||
|
border-bottom: 1px solid var(--theme-border);
|
||||||
|
border-top: 1px solid var(--theme-border);
|
||||||
|
}
|
||||||
|
|
||||||
|
.content:not(.noPadding) {
|
||||||
|
padding: 15px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.footer {
|
||||||
|
border-bottom: 1px solid var(--theme-border);
|
||||||
|
padding: 15px;
|
||||||
|
background-color: var(--theme-bg-modalheader);
|
||||||
|
}
|
||||||
|
</style>
|
||||||
7
packages/web/src/modals/ModalLayer.svelte
Normal file
7
packages/web/src/modals/ModalLayer.svelte
Normal file
@@ -0,0 +1,7 @@
|
|||||||
|
<script>
|
||||||
|
import { openedModals } from '../stores';
|
||||||
|
</script>
|
||||||
|
|
||||||
|
{#each $openedModals as { component, props, modalId }}
|
||||||
|
<svelte:component this={component} {modalId} {...props} />
|
||||||
|
{/each}
|
||||||
11
packages/web/src/modals/modalTools.ts
Normal file
11
packages/web/src/modals/modalTools.ts
Normal file
@@ -0,0 +1,11 @@
|
|||||||
|
import { openedModals } from '../stores';
|
||||||
|
import uuidv1 from 'uuid/v1';
|
||||||
|
|
||||||
|
export function showModal(component, props = {}) {
|
||||||
|
const modalId = uuidv1();
|
||||||
|
openedModals.update(x => [...x, { component, modalId, props }]);
|
||||||
|
}
|
||||||
|
|
||||||
|
export function closeModal(modalId) {
|
||||||
|
openedModals.update(x => x.filter(y => y.modalId != modalId));
|
||||||
|
}
|
||||||
@@ -48,6 +48,11 @@
|
|||||||
--theme-bg-selected: #15395b; /* blue-3 */
|
--theme-bg-selected: #15395b; /* blue-3 */
|
||||||
|
|
||||||
--theme-bg-statusbar-inv: blue;
|
--theme-bg-statusbar-inv: blue;
|
||||||
|
--theme-bg-modalheader: rgb(43, 60, 61);
|
||||||
|
|
||||||
|
--theme-bg-button-inv: #004488;
|
||||||
|
--theme-bg-button-inv-2: #1a5794;
|
||||||
|
--theme-bg-button-inv-3: #346aa0;
|
||||||
|
|
||||||
--theme-icon-blue: #3c9ae8;
|
--theme-icon-blue: #3c9ae8;
|
||||||
--theme-icon-green: #8fd460;
|
--theme-icon-green: #8fd460;
|
||||||
|
|||||||
@@ -41,6 +41,11 @@
|
|||||||
--theme-bg-selected: #91d5ff; /* blue-3 */
|
--theme-bg-selected: #91d5ff; /* blue-3 */
|
||||||
|
|
||||||
--theme-bg-statusbar-inv: blue;
|
--theme-bg-statusbar-inv: blue;
|
||||||
|
--theme-bg-modalheader: #eff;
|
||||||
|
|
||||||
|
--theme-bg-button-inv: #337ab7;
|
||||||
|
--theme-bg-button-inv-2: #4d8bc0;
|
||||||
|
--theme-bg-button-inv-3: #679cc9;
|
||||||
|
|
||||||
--theme-icon-blue: #096dd9; /* blue-7 */
|
--theme-icon-blue: #096dd9; /* blue-7 */
|
||||||
--theme-icon-green: #237804; /* green-7 */
|
--theme-icon-green: #237804; /* green-7 */
|
||||||
@@ -51,5 +56,6 @@
|
|||||||
|
|
||||||
--theme-icon-inv-green: #8fd460;
|
--theme-icon-inv-green: #8fd460;
|
||||||
--theme-icon-inv-red: #e84749;
|
--theme-icon-inv-red: #e84749;
|
||||||
|
|
||||||
}
|
}
|
||||||
</style>
|
</style>
|
||||||
|
|||||||
@@ -36,8 +36,8 @@ export const activeTabId = derived([openedTabs], ([$openedTabs]) => $openedTabs.
|
|||||||
export const visibleToolbar = writableWithStorage(1, 'visibleToolbar');
|
export const visibleToolbar = writableWithStorage(1, 'visibleToolbar');
|
||||||
export const leftPanelWidth = writable(300);
|
export const leftPanelWidth = writable(300);
|
||||||
export const currentDropDownMenu = writable(null);
|
export const currentDropDownMenu = writable(null);
|
||||||
|
export const openedModals = writable([]);
|
||||||
|
|
||||||
subscribeCssVariable(selectedWidget, x => (x ? 1 : 0), '--dim-visible-left-panel');
|
subscribeCssVariable(selectedWidget, x => (x ? 1 : 0), '--dim-visible-left-panel');
|
||||||
subscribeCssVariable(visibleToolbar, x => (x ? 1 : 0), '--dim-visible-toolbar');
|
subscribeCssVariable(visibleToolbar, x => (x ? 1 : 0), '--dim-visible-toolbar');
|
||||||
subscribeCssVariable(leftPanelWidth, x => `${x}px`, '--dim-left-panel-width');
|
subscribeCssVariable(leftPanelWidth, x => `${x}px`, '--dim-left-panel-width');
|
||||||
|
|
||||||
|
|||||||
38
packages/web/src/widgets/FormStyledButton.svelte
Normal file
38
packages/web/src/widgets/FormStyledButton.svelte
Normal file
@@ -0,0 +1,38 @@
|
|||||||
|
<script lang="ts">
|
||||||
|
import { createEventDispatcher } from 'svelte';
|
||||||
|
|
||||||
|
const dispatch = createEventDispatcher();
|
||||||
|
|
||||||
|
export let type = 'button';
|
||||||
|
export let disabled = false;
|
||||||
|
export let value;
|
||||||
|
|
||||||
|
function handleClick() {
|
||||||
|
if (disabled) dispatch('click');
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<input {type} {value} class:disabled {...$$restProps} on:click={handleClick} />
|
||||||
|
|
||||||
|
<style>
|
||||||
|
input {
|
||||||
|
border: 1px solid var(--theme-bg-button-inv-2);
|
||||||
|
padding: 5px;
|
||||||
|
margin: 2px;
|
||||||
|
width: 100px;
|
||||||
|
background-color: var(--theme-bg-button-inv);
|
||||||
|
color: var(--theme-font-inv-1);
|
||||||
|
border-radius: 2px;
|
||||||
|
}
|
||||||
|
|
||||||
|
input:hover:not(.disabled) {
|
||||||
|
background-color: var(--theme-bg-button-inv-2);
|
||||||
|
}
|
||||||
|
input:active:not(.disabled) {
|
||||||
|
background-color: var(--theme-bg-button-inv-3);
|
||||||
|
}
|
||||||
|
input.disabled {
|
||||||
|
background-color: var(--theme-bg-button-inv-3);
|
||||||
|
color: var(--theme-font-inv-3);
|
||||||
|
}
|
||||||
|
</style>
|
||||||
Reference in New Issue
Block a user