Use fixed ComponentDetail popup

This commit is contained in:
the1812 2021-11-07 23:07:33 +08:00
parent 4cb86a92bb
commit cdb64c3afa
2 changed files with 61 additions and 35 deletions

View File

@ -16,7 +16,7 @@
{{ t.displayName }} {{ t.displayName }}
</div> </div>
</div> </div>
<div class="component-detail-separator"></div> <!-- <div class="component-detail-separator"></div> -->
<template <template
v-if="(componentData.options && generatedOptions.length > 0) || componentData.extraOptions" v-if="(componentData.options && generatedOptions.length > 0) || componentData.extraOptions"
> >
@ -37,12 +37,16 @@
</div> </div>
<slot></slot> <slot></slot>
</div> </div>
<div class="component-detail-separator"></div> <!-- <div class="component-detail-separator"></div> -->
</template> </template>
<template v-if="!(componentData.options && !componentData.description)"> <template v-if="!(componentData.options && !componentData.description)">
<ComponentDescription :component-data="componentData" /> <ComponentDescription
<div class="component-detail-separator"></div> class="component-detail-description"
:component-data="componentData"
/>
<!-- <div class="component-detail-separator"></div> -->
</template> </template>
<div class="component-detail-grow"></div>
<div class="component-detail-internal-data"> <div class="component-detail-internal-data">
<div class="internal-name"> <div class="internal-name">
内部名称: {{ componentData.name }} 内部名称: {{ componentData.name }}
@ -139,6 +143,11 @@ export default Vue.extend({
.component-detail { .component-detail {
min-width: 264px; min-width: 264px;
width: 264px; width: 264px;
flex: 1;
background-color: inherit;
border-radius: 7px;
@include no-scrollbar();
@include v-stretch();
&-separator { &-separator {
height: 1px; height: 1px;
background-color: #8882; background-color: #8882;
@ -149,7 +158,12 @@ export default Vue.extend({
&-header { &-header {
@include h-center(); @include h-center();
justify-content: space-between; justify-content: space-between;
margin-bottom: 12px; padding: 12px;
background-color: inherit;
position: sticky;
top: 0;
z-index: 2;
.display-name { .display-name {
font-weight: bold; font-weight: bold;
font-size: 16px; font-size: 16px;
@ -161,13 +175,16 @@ export default Vue.extend({
} }
} }
} }
.component-description:not(:last-child) { &-description:not(:last-child) {
margin-bottom: 12px; padding: 12px 12px 0;
// max-height: 9em;
// line-height: 1.5;
// @include no-scrollbar();
} }
&-tags { &-tags {
@include h-center(); @include h-center();
flex-wrap: wrap; flex-wrap: wrap;
margin-bottom: 8px; padding: 0 8px 8px;
.tag { .tag {
@include h-center(); @include h-center();
@include card(); @include card();
@ -187,7 +204,12 @@ export default Vue.extend({
} }
&-internal-data { &-internal-data {
@include h-center(); @include h-center();
position: sticky;
bottom: 0;
justify-content: space-between; justify-content: space-between;
min-height: 24px;
background-color: inherit;
padding: 8px 12px;
.internal-name { .internal-name {
opacity: 0.5; opacity: 0.5;
@ -240,7 +262,11 @@ export default Vue.extend({
} }
} }
&-options { &-options {
margin-bottom: 12px; padding: 8px 12px;
// flex: 1 0 0;
// height: 0;
// @include no-scrollbar();
.component-detail-options-title { .component-detail-options-title {
font-weight: bold; font-weight: bold;
font-size: 14px; font-size: 14px;
@ -250,5 +276,8 @@ export default Vue.extend({
margin-bottom: 4px; margin-bottom: 4px;
} }
} }
&-grow {
flex: 1;
}
} }
</style> </style>

View File

@ -30,7 +30,7 @@
<ComponentSettings <ComponentSettings
v-for="c of renderedComponents" v-for="c of renderedComponents"
:key="c.name" :key="c.name"
:class="{ selected: selectedComponent === c }" :class="{ selected: selectedComponent === c && componentDetailOpen }"
:component-data="c" :component-data="c"
:data-name="c.name" :data-name="c.name"
@click.native="selectComponent(c)" @click.native="selectComponent(c)"
@ -43,7 +43,7 @@
ref="detailsPopup" ref="detailsPopup"
class="component-detail-panel" class="component-detail-panel"
:trigger-element="$refs.componentList" :trigger-element="$refs.componentList"
:open="Boolean(selectedComponent)" :open="componentDetailOpen"
@popup-change="!$event && closePopper()" @popup-change="!$event && closePopper()"
> >
<ComponentDetail <ComponentDetail
@ -51,7 +51,6 @@
:key="selectedComponent.name" :key="selectedComponent.name"
:component-data="selectedComponent" :component-data="selectedComponent"
@close="closePopper()" @close="closePopper()"
@mounted="updatePopper()"
/> />
</VPopup> </VPopup>
</div> </div>
@ -65,9 +64,6 @@ import {
VPopup, VPopup,
VEmpty, VEmpty,
} from '@/ui' } from '@/ui'
import { createPopper } from '@popperjs/core'
import { dq } from '@/core/utils'
import { addComponentListener } from '@/core/settings'
import { getHook } from '@/plugins/hook' import { getHook } from '@/plugins/hook'
import ComponentSettings from './ComponentSettings.vue' import ComponentSettings from './ComponentSettings.vue'
import { import {
@ -77,7 +73,6 @@ import ComponentDetail from './ComponentDetail.vue'
import ComponentTags from './ComponentTags.vue' import ComponentTags from './ComponentTags.vue'
import { getDescriptionText } from '../description' import { getDescriptionText } from '../description'
let activePopper: ReturnType<typeof createPopper>
const defaultSearchFilter = (items: ComponentMetadata[]) => items const defaultSearchFilter = (items: ComponentMetadata[]) => items
export default { export default {
name: 'SettingsPanel', name: 'SettingsPanel',
@ -95,6 +90,7 @@ export default {
components, components,
renderedComponents: components.filter(c => !c.hidden), renderedComponents: components.filter(c => !c.hidden),
selectedComponent: null, selectedComponent: null,
componentDetailOpen: false,
collasped: false, collasped: false,
peek: false, peek: false,
searchKeyword: '', searchKeyword: '',
@ -137,24 +133,15 @@ export default {
} }
}, },
}, },
mounted() {
addComponentListener('settingsPanel.dockSide', () => {
this.updatePopper()
})
},
methods: { methods: {
updatePopper() {
activePopper?.update()
},
closePopper() { closePopper() {
activePopper?.destroy() this.componentDetailOpen = false
this.selectedComponent = null
}, },
selectComponent(component: ComponentMetadata) { selectComponent(component: ComponentMetadata) {
const closeHooks = getHook('settingsPanel.componentDetail.close') const closeHooks = getHook('settingsPanel.componentDetail.close')
const openHooks = getHook('settingsPanel.componentDetail.open') const openHooks = getHook('settingsPanel.componentDetail.open')
const selectedName = this.selectedComponent?.name const selectedName = this.selectedComponent?.name
const isAlreadySelected = selectedName === component.name const isAlreadySelected = this.componentDetailOpen && selectedName === component.name
closeHooks.before(selectedName) closeHooks.before(selectedName)
this.closePopper() this.closePopper()
closeHooks.after(selectedName) closeHooks.after(selectedName)
@ -163,13 +150,7 @@ export default {
} }
openHooks.before(component.name) openHooks.before(component.name)
this.selectedComponent = component this.selectedComponent = component
activePopper = createPopper( this.componentDetailOpen = true
dq(`.component-settings[data-name=${component.name}]`),
this.$refs.detailsPopup.$el,
{
placement: 'right',
},
)
openHooks.after(component.name) openHooks.after(component.name)
}, },
updateRenderedComponents() { updateRenderedComponents() {
@ -306,7 +287,23 @@ export default {
} }
.component-detail-panel { .component-detail-panel {
@include card(); @include card();
padding: 12px; @include v-stretch();
top: 50%;
left: calc(100% - 12px);
height: calc(100% - 22px);
z-index: -1;
transform: translateZ(0) translateY(-50%) translateX(calc(-48% * var(--direction)));
transition: transform 0.3s cubic-bezier(0.22, 0.61, 0.36, 1),
opacity 0.3s cubic-bezier(0.22, 0.61, 0.36, 1);
padding-left: 12px;
body.settings-panel-dock-right & {
left: unset;
right: calc(100% - 12px);
padding: 0 12px 0 0;
}
&.open {
transform: translateZ(0) translateY(-50%) translateX(0);
}
} }
&.collasped { &.collasped {
height: auto; height: auto;