feat: add filter input to browser pane
This commit is contained in:
parent
379bb5e623
commit
8201004478
|
@ -25,6 +25,7 @@ const props = defineProps({
|
||||||
border: Boolean,
|
border: Boolean,
|
||||||
disabled: Boolean,
|
disabled: Boolean,
|
||||||
buttonStyle: [String, Object],
|
buttonStyle: [String, Object],
|
||||||
|
buttonClass: [String, Object],
|
||||||
})
|
})
|
||||||
|
|
||||||
const hasTooltip = computed(() => {
|
const hasTooltip = computed(() => {
|
||||||
|
@ -36,6 +37,7 @@ const hasTooltip = computed(() => {
|
||||||
<n-tooltip v-if="hasTooltip" :show-arrow="false">
|
<n-tooltip v-if="hasTooltip" :show-arrow="false">
|
||||||
<template #trigger>
|
<template #trigger>
|
||||||
<n-button
|
<n-button
|
||||||
|
:class="props.buttonClass"
|
||||||
:color="props.color"
|
:color="props.color"
|
||||||
:disabled="disabled"
|
:disabled="disabled"
|
||||||
:focusable="false"
|
:focusable="false"
|
||||||
|
@ -57,10 +59,12 @@ const hasTooltip = computed(() => {
|
||||||
</n-tooltip>
|
</n-tooltip>
|
||||||
<n-button
|
<n-button
|
||||||
v-else
|
v-else
|
||||||
|
:class="props.buttonClass"
|
||||||
:color="props.color"
|
:color="props.color"
|
||||||
:disabled="disabled"
|
:disabled="disabled"
|
||||||
:focusable="false"
|
:focusable="false"
|
||||||
:loading="loading"
|
:loading="loading"
|
||||||
|
:style="props.buttonStyle"
|
||||||
:text="!border"
|
:text="!border"
|
||||||
:type="type"
|
:type="type"
|
||||||
@click.prevent="emit('click')">
|
@click.prevent="emit('click')">
|
||||||
|
|
|
@ -94,26 +94,13 @@ const viewLanguage = computed(() => {
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
|
|
||||||
const btnStyle = computed(() => ({
|
|
||||||
padding: '3px',
|
|
||||||
border: 'solid 1px #0000',
|
|
||||||
borderRadius: '3px',
|
|
||||||
}))
|
|
||||||
|
|
||||||
const pinBtnStyle = computed(() => ({
|
|
||||||
padding: '3px',
|
|
||||||
border: `solid 1px ${themeVars.value.borderColor}`,
|
|
||||||
borderRadius: '3px',
|
|
||||||
backgroundColor: themeVars.value.borderColor,
|
|
||||||
}))
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* @param {decodeTypes} decode
|
* @param {decodeTypes|null} decode
|
||||||
* @param {formatTypes} format
|
* @param {formatTypes|null} format
|
||||||
* @return {Promise<void>}
|
* @return {Promise<void>}
|
||||||
*/
|
*/
|
||||||
const onFormatChanged = async (decode = '', format = '') => {
|
const onFormatChanged = async (decode = null, format = null) => {
|
||||||
try {
|
try {
|
||||||
loading.value = true
|
loading.value = true
|
||||||
const {
|
const {
|
||||||
|
@ -196,21 +183,21 @@ const onSave = () => {
|
||||||
<template #header-extra>
|
<template #header-extra>
|
||||||
<n-space :size="5">
|
<n-space :size="5">
|
||||||
<icon-button
|
<icon-button
|
||||||
:button-style="isPin ? pinBtnStyle : btnStyle"
|
:button-class="{ 'pinable-btn': true, 'unpin-btn': !isPin, 'pin-btn': isPin }"
|
||||||
:icon="Pin"
|
:icon="Pin"
|
||||||
:size="19"
|
:size="19"
|
||||||
:t-tooltip="isPin ? 'interface.unpin_edit' : 'interface.pin_edit'"
|
:t-tooltip="isPin ? 'interface.unpin_edit' : 'interface.pin_edit'"
|
||||||
stroke-width="4"
|
stroke-width="4"
|
||||||
@click="isPin = !isPin" />
|
@click="isPin = !isPin" />
|
||||||
<icon-button
|
<icon-button
|
||||||
:button-style="btnStyle"
|
:button-class="['pinable-btn', 'unpin-btn']"
|
||||||
:icon="props.fullscreen ? OffScreen : FullScreen"
|
:icon="props.fullscreen ? OffScreen : FullScreen"
|
||||||
:size="18"
|
:size="18"
|
||||||
stroke-width="5"
|
stroke-width="5"
|
||||||
t-tooltip="interface.fullscreen"
|
t-tooltip="interface.fullscreen"
|
||||||
@click="onToggleFullscreen" />
|
@click="onToggleFullscreen" />
|
||||||
<icon-button
|
<icon-button
|
||||||
:button-style="btnStyle"
|
:button-class="['pinable-btn', 'unpin-btn']"
|
||||||
:icon="WindowClose"
|
:icon="WindowClose"
|
||||||
:size="18"
|
:size="18"
|
||||||
stroke-width="5"
|
stroke-width="5"
|
||||||
|
@ -267,6 +254,22 @@ const onSave = () => {
|
||||||
background-color: unset;
|
background-color: unset;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
:deep(.pinable-btn) {
|
||||||
|
padding: 3px;
|
||||||
|
border-style: solid;
|
||||||
|
border-width: 1px;
|
||||||
|
border-radius: 3px;
|
||||||
|
}
|
||||||
|
|
||||||
|
:deep(.unpin-btn) {
|
||||||
|
border-color: #0000;
|
||||||
|
}
|
||||||
|
|
||||||
|
:deep(.pin-btn) {
|
||||||
|
border-color: v-bind('themeVars.borderColor');
|
||||||
|
background-color: v-bind('themeVars.borderColor');
|
||||||
|
}
|
||||||
|
|
||||||
//:deep(.n-card--bordered) {
|
//:deep(.n-card--bordered) {
|
||||||
// border-radius: 0;
|
// border-radius: 0;
|
||||||
//}
|
//}
|
||||||
|
|
|
@ -2,6 +2,14 @@
|
||||||
import { computed, reactive } from 'vue'
|
import { computed, reactive } from 'vue'
|
||||||
import { debounce, isEmpty, trim } from 'lodash'
|
import { debounce, isEmpty, trim } from 'lodash'
|
||||||
import { NButton, NInput } from 'naive-ui'
|
import { NButton, NInput } from 'naive-ui'
|
||||||
|
import IconButton from '@/components/common/IconButton.vue'
|
||||||
|
|
||||||
|
const props = defineProps({
|
||||||
|
fullSearchIcon: {
|
||||||
|
type: [String, Object],
|
||||||
|
default: null,
|
||||||
|
},
|
||||||
|
})
|
||||||
|
|
||||||
const emit = defineEmits(['filterChanged', 'matchChanged'])
|
const emit = defineEmits(['filterChanged', 'matchChanged'])
|
||||||
|
|
||||||
|
@ -58,6 +66,7 @@ defineExpose({
|
||||||
|
|
||||||
<template>
|
<template>
|
||||||
<n-input-group>
|
<n-input-group>
|
||||||
|
<slot name="prepend" />
|
||||||
<n-input
|
<n-input
|
||||||
v-model:value="inputData.filter"
|
v-model:value="inputData.filter"
|
||||||
:placeholder="$t('interface.filter')"
|
:placeholder="$t('interface.filter')"
|
||||||
|
@ -75,9 +84,17 @@ defineExpose({
|
||||||
</n-tooltip>
|
</n-tooltip>
|
||||||
</template>
|
</template>
|
||||||
</n-input>
|
</n-input>
|
||||||
<n-button :disabled="hasMatch && !hasFilter" :focusable="false" @click="onFullSearch">
|
<icon-button
|
||||||
|
v-if="props.fullSearchIcon"
|
||||||
|
:disabled="hasMatch && !hasFilter"
|
||||||
|
:icon="props.fullSearchIcon"
|
||||||
|
border
|
||||||
|
t-tooltip="interface.full_search"
|
||||||
|
@click="onFullSearch" />
|
||||||
|
<n-button v-else :disabled="hasMatch && !hasFilter" :focusable="false" @click="onFullSearch">
|
||||||
{{ $t('interface.full_search') }}
|
{{ $t('interface.full_search') }}
|
||||||
</n-button>
|
</n-button>
|
||||||
|
<slot name="append" />
|
||||||
</n-input-group>
|
</n-input-group>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
<script setup>
|
<script setup>
|
||||||
import { NIcon, useThemeVars } from 'naive-ui'
|
import { useThemeVars } from 'naive-ui'
|
||||||
import BrowserTree from './BrowserTree.vue'
|
import BrowserTree from './BrowserTree.vue'
|
||||||
import IconButton from '@/components/common/IconButton.vue'
|
import IconButton from '@/components/common/IconButton.vue'
|
||||||
import useTabStore from 'stores/tab.js'
|
import useTabStore from 'stores/tab.js'
|
||||||
|
@ -11,6 +11,8 @@ import { useI18n } from 'vue-i18n'
|
||||||
import { types } from '@/consts/support_redis_type.js'
|
import { types } from '@/consts/support_redis_type.js'
|
||||||
import Search from '@/components/icons/Search.vue'
|
import Search from '@/components/icons/Search.vue'
|
||||||
import Unlink from '@/components/icons/Unlink.vue'
|
import Unlink from '@/components/icons/Unlink.vue'
|
||||||
|
import Filter from '@/components/icons/Filter.vue'
|
||||||
|
import ContentSearchInput from '@/components/content_value/ContentSearchInput.vue'
|
||||||
|
|
||||||
const themeVars = useThemeVars()
|
const themeVars = useThemeVars()
|
||||||
const dialogStore = useDialogStore()
|
const dialogStore = useDialogStore()
|
||||||
|
@ -60,24 +62,9 @@ const filterTypeOptions = computed(() => {
|
||||||
<template>
|
<template>
|
||||||
<div class="nav-pane-container flex-box-v">
|
<div class="nav-pane-container flex-box-v">
|
||||||
<browser-tree ref="browserTreeRef" :server="currentName" />
|
<browser-tree ref="browserTreeRef" :server="currentName" />
|
||||||
|
s
|
||||||
<div v-if="filterForm.showFilter" class="nav-pane-bottom flex-box-h">
|
|
||||||
<n-input-group>
|
|
||||||
<n-select
|
|
||||||
v-model:value="filterForm.type"
|
|
||||||
:consistent-menu-width="false"
|
|
||||||
:options="filterTypeOptions"
|
|
||||||
style="width: 120px" />
|
|
||||||
<n-input clearable placeholder="" />
|
|
||||||
<n-button :focusable="false" ghost>
|
|
||||||
<template #icon>
|
|
||||||
<n-icon :component="Search" />
|
|
||||||
</template>
|
|
||||||
</n-button>
|
|
||||||
</n-input-group>
|
|
||||||
</div>
|
|
||||||
<!-- bottom function bar -->
|
<!-- bottom function bar -->
|
||||||
<div class="nav-pane-bottom flex-box-h">
|
<div class="nav-pane-bottom flex-box-v">
|
||||||
<!-- <switch-button-->
|
<!-- <switch-button-->
|
||||||
<!-- v-model:value="viewType"-->
|
<!-- v-model:value="viewType"-->
|
||||||
<!-- :icons="[TreeView, ListView]"-->
|
<!-- :icons="[TreeView, ListView]"-->
|
||||||
|
@ -86,9 +73,58 @@ const filterTypeOptions = computed(() => {
|
||||||
<!-- unselect-stroke-width="3"-->
|
<!-- unselect-stroke-width="3"-->
|
||||||
<!-- @update:value="onSwitchView" />-->
|
<!-- @update:value="onSwitchView" />-->
|
||||||
<!-- <icon-button :icon="Status" size="20" stroke-width="4" t-tooltip="interface.status" @click="onInfo" />-->
|
<!-- <icon-button :icon="Status" size="20" stroke-width="4" t-tooltip="interface.status" @click="onInfo" />-->
|
||||||
<icon-button :icon="Refresh" size="20" stroke-width="4" t-tooltip="interface.reload" @click="onRefresh" />
|
<div
|
||||||
|
v-show="filterForm.showFilter"
|
||||||
|
class="flex-box-h nav-pane-func"
|
||||||
|
style="padding-left: 3px; padding-right: 3px">
|
||||||
|
<!-- <n-input-group v-show="filterForm.showFilter">-->
|
||||||
|
<!-- <n-select-->
|
||||||
|
<!-- v-model:value="filterForm.type"-->
|
||||||
|
<!-- :consistent-menu-width="false"-->
|
||||||
|
<!-- :options="filterTypeOptions"-->
|
||||||
|
<!-- style="width: 120px" />-->
|
||||||
|
<!-- <n-input clearable placeholder="">-->
|
||||||
|
<!-- <template #prefix></template>-->
|
||||||
|
<!-- </n-input>-->
|
||||||
|
<!-- <n-button :focusable="false" ghost>-->
|
||||||
|
<!-- <template #icon>-->
|
||||||
|
<!-- <n-icon :component="Search" />-->
|
||||||
|
<!-- </template>-->
|
||||||
|
<!-- </n-button>-->
|
||||||
|
<!-- </n-input-group>-->
|
||||||
|
<content-search-input :full-search-icon="Search">
|
||||||
|
<template #prepend>
|
||||||
|
<n-select
|
||||||
|
v-model:value="filterForm.type"
|
||||||
|
:consistent-menu-width="false"
|
||||||
|
:options="filterTypeOptions"
|
||||||
|
style="width: 120px" />
|
||||||
|
</template>
|
||||||
|
</content-search-input>
|
||||||
|
</div>
|
||||||
|
<div class="flex-box-h nav-pane-func">
|
||||||
|
<icon-button
|
||||||
|
:button-class="{
|
||||||
|
'filter-on': filterForm.showFilter,
|
||||||
|
'filter-off': !filterForm.showFilter,
|
||||||
|
'toggle-btn': true,
|
||||||
|
'nav-pane-func-btn': true,
|
||||||
|
}"
|
||||||
|
:icon="Filter"
|
||||||
|
size="20"
|
||||||
|
stroke-width="4"
|
||||||
|
t-tooltip="interface.filter_key"
|
||||||
|
@click="filterForm.showFilter = !filterForm.showFilter" />
|
||||||
|
<icon-button
|
||||||
|
:button-class="['nav-pane-func-btn']"
|
||||||
|
:icon="Refresh"
|
||||||
|
size="20"
|
||||||
|
stroke-width="4"
|
||||||
|
t-tooltip="interface.reload"
|
||||||
|
@click="onRefresh" />
|
||||||
<div class="flex-item-expand" />
|
<div class="flex-item-expand" />
|
||||||
<icon-button
|
<icon-button
|
||||||
|
:button-class="['nav-pane-func-btn']"
|
||||||
:icon="Unlink"
|
:icon="Unlink"
|
||||||
size="20"
|
size="20"
|
||||||
stroke-width="4"
|
stroke-width="4"
|
||||||
|
@ -96,9 +132,24 @@ const filterTypeOptions = computed(() => {
|
||||||
@click="onDisconnect" />
|
@click="onDisconnect" />
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
<style lang="scss" scoped>
|
<style lang="scss" scoped>
|
||||||
|
:deep(.toggle-btn) {
|
||||||
|
border-style: solid;
|
||||||
|
border-width: 1px;
|
||||||
|
}
|
||||||
|
|
||||||
|
:deep(.filter-on) {
|
||||||
|
border-color: v-bind('themeVars.borderColor');
|
||||||
|
background-color: v-bind('themeVars.borderColor');
|
||||||
|
}
|
||||||
|
|
||||||
|
:deep(.filter-off) {
|
||||||
|
border-color: #0000;
|
||||||
|
}
|
||||||
|
|
||||||
.nav-pane-bottom {
|
.nav-pane-bottom {
|
||||||
color: v-bind('themeVars.iconColor');
|
color: v-bind('themeVars.iconColor');
|
||||||
border-top: v-bind('themeVars.borderColor') 1px solid;
|
border-top: v-bind('themeVars.borderColor') 1px solid;
|
||||||
|
|
|
@ -18,14 +18,16 @@ const filterPattern = ref('')
|
||||||
<connection-tree :filter-pattern="filterPattern" />
|
<connection-tree :filter-pattern="filterPattern" />
|
||||||
|
|
||||||
<!-- bottom function bar -->
|
<!-- bottom function bar -->
|
||||||
<div class="nav-pane-bottom flex-box-h">
|
<div class="nav-pane-bottom nav-pane-func flex-box-h">
|
||||||
<icon-button
|
<icon-button
|
||||||
|
:button-class="['nav-pane-func-btn']"
|
||||||
:icon="AddLink"
|
:icon="AddLink"
|
||||||
size="20"
|
size="20"
|
||||||
stroke-width="4"
|
stroke-width="4"
|
||||||
t-tooltip="interface.new_conn"
|
t-tooltip="interface.new_conn"
|
||||||
@click="dialogStore.openNewDialog()" />
|
@click="dialogStore.openNewDialog()" />
|
||||||
<icon-button
|
<icon-button
|
||||||
|
:button-class="['nav-pane-func-btn']"
|
||||||
:icon="AddGroup"
|
:icon="AddGroup"
|
||||||
size="20"
|
size="20"
|
||||||
stroke-width="4"
|
stroke-width="4"
|
||||||
|
|
|
@ -130,12 +130,17 @@ body {
|
||||||
.nav-pane-container {
|
.nav-pane-container {
|
||||||
overflow: hidden;
|
overflow: hidden;
|
||||||
|
|
||||||
.nav-pane-bottom {
|
.nav-pane-func {
|
||||||
align-items: center;
|
align-items: center;
|
||||||
gap: 8px;
|
gap: 3px;
|
||||||
padding: 3px 10px 3px 10px;
|
padding: 3px 8px;
|
||||||
min-height: 30px;
|
min-height: 30px;
|
||||||
//border-top: v-bind('themeVars.borderColor') 1px solid;
|
|
||||||
|
.nav-pane-func-btn {
|
||||||
|
padding: 3px;
|
||||||
|
border-radius: 3px;
|
||||||
|
box-sizing: border-box;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue