fix MainLayout.vue content height

This commit is contained in:
Timi
2026-04-03 23:44:46 +08:00
parent d819249ebf
commit 594d1b4222
9 changed files with 531 additions and 177 deletions

View File

@@ -1,58 +1,135 @@
<template>
<t-cell-group theme="card" class="file-explorer-list">
<recycle-scroller
class="scroller"
:items="items"
:item-size="56"
key-field="path"
v-slot="{ item }"
>
<recycle-scroller
class="file-explorer-list"
:items="items"
:item-size="56"
key-field="path"
>
<template #before>
<div aria-hidden="true" class="spacer top"></div>
</template>
<template #default="{ item }">
<t-swipe-cell>
<t-cell
class="cell"
:title="item.name"
:arrow="item.type === 'dir'"
:note="item.size"
@click="emit('open', item)"
@click="handleOpen(item)"
>
<template #note>
<div class="note">
<t-loading v-if="item.path === pendingPath" size="1rem" />
<span v-if="item.type === 'file'" v-text="item.size"></span>
</div>
</template>
<template #left-icon>
<t-icon :name="item.type === 'dir' ? 'folder' : item.icon" />
</template>
</t-cell>
</t-swipe-cell>
</recycle-scroller>
</t-cell-group>
</template>
<template #after>
<div aria-hidden="true" class="spacer bottom"></div>
</template>
</recycle-scroller>
</template>
<script setup lang="ts">
import { RecycleScroller } from "vue-virtual-scroller";
import { type ExplorerItem } from "./fileExplorer.shared";
defineProps<{
const props = defineProps<{
items: ExplorerItem[];
pendingPath?: string;
}>();
const emit = defineEmits<{
open: [item: ExplorerItem];
}>();
function handleOpen(item: ExplorerItem): void {
if (props.pendingPath) {
return;
}
emit("open", item);
}
</script>
<style scoped lang="less">
.file-explorer-list {
overflow: hidden;
--top-gap: var(--page-top-gap, 1rem);
--bottom-gap: 5.5rem;
:deep(.t-cell-group) {
margin: 0;
flex: 1 1 auto;
height: 100%;
padding: 0 1rem;
display: flex;
overflow: hidden;
min-height: 0;
flex-direction: column;
&:deep(.vue-recycle-scroller__item-view) {
&:first-child {
.cell {
border-radius: var(--td-radius-large) var(--td-radius-large) 0 0;
}
}
&:last-child {
.cell {
border-radius: 0 0 var(--td-radius-large) var(--td-radius-large);
&:after {
border-bottom: 0;
}
}
}
}
.scroller {
height: 100%;
.spacer {
width: 100%;
pointer-events: none;
.vue-recycle-scroller__item-view {
&.top {
height: var(--top-gap);
}
&:last-child .cell:after {
border-bottom: 0;
}
&.bottom {
height: var(--bottom-gap);
}
}
.note {
gap: .375rem;
display: flex;
flex: 0 0 auto;
min-height: 1rem;
align-items: center;
white-space: nowrap;
color: var(--app-sub);
}
.cell {
&:deep(.t-cell__title) {
flex: 1 1 auto;
overflow: hidden;
min-width: 0;
}
&:deep(.t-cell__title-text) {
overflow: hidden;
white-space: nowrap;
text-overflow: ellipsis;
}
&:deep(.t-cell__note) {
flex: 0 0 auto;
white-space: nowrap;
}
}
}