feat: topic page aside fold
This commit is contained in:
parent
4ec4eb3222
commit
e07274b7b6
|
@ -46,6 +46,9 @@ interface Topic {
|
||||||
replyRequest: TopicReplyRequestData
|
replyRequest: TopicReplyRequestData
|
||||||
// 评论的缓存
|
// 评论的缓存
|
||||||
commentDraft: CommentDraft
|
commentDraft: CommentDraft
|
||||||
|
|
||||||
|
// 当前页面话题的 tags,用于获取相关话题
|
||||||
|
currentTags: string[]
|
||||||
}
|
}
|
||||||
|
|
||||||
export const useKUNGalgameTopicStore = defineStore({
|
export const useKUNGalgameTopicStore = defineStore({
|
||||||
|
@ -74,6 +77,8 @@ export const useKUNGalgameTopicStore = defineStore({
|
||||||
to_uid: 0,
|
to_uid: 0,
|
||||||
content: '',
|
content: '',
|
||||||
},
|
},
|
||||||
|
|
||||||
|
currentTags: [],
|
||||||
}),
|
}),
|
||||||
actions: {
|
actions: {
|
||||||
// 左侧相同标签下的其它话题
|
// 左侧相同标签下的其它话题
|
||||||
|
|
|
@ -8,19 +8,12 @@ import {
|
||||||
defineAsyncComponent,
|
defineAsyncComponent,
|
||||||
onBeforeMount,
|
onBeforeMount,
|
||||||
computed,
|
computed,
|
||||||
|
provide,
|
||||||
} from 'vue'
|
} from 'vue'
|
||||||
import { onBeforeRouteLeave } from 'vue-router'
|
import { onBeforeRouteLeave } from 'vue-router'
|
||||||
|
|
||||||
import TopicAsideNav from './aside/TopicAsideNav.vue'
|
// Aside
|
||||||
|
import Aside from './aside/Aside.vue'
|
||||||
// 相同标签下的其它话题
|
|
||||||
import TopicOtherTag from './aside/TopicOtherTag.vue'
|
|
||||||
|
|
||||||
// 楼主的其它话题
|
|
||||||
import TopicMaster from './aside/TopicMaster.vue'
|
|
||||||
|
|
||||||
// 导入 Footer
|
|
||||||
import KUNGalgameFooter from '@/components/KUNGalgameFooter.vue'
|
|
||||||
import Master from './components/Master.vue'
|
import Master from './components/Master.vue'
|
||||||
import Reply from './components/Reply.vue'
|
import Reply from './components/Reply.vue'
|
||||||
// 异步导入回复面板
|
// 异步导入回复面板
|
||||||
|
@ -48,6 +41,9 @@ const topicStore = useKUNGalgameTopicStore()
|
||||||
|
|
||||||
const requestData = storeToRefs(useKUNGalgameTopicStore())
|
const requestData = storeToRefs(useKUNGalgameTopicStore())
|
||||||
|
|
||||||
|
const { showKUNGalgamePageWidth } = storeToRefs(settingsStore)
|
||||||
|
const { isShowAdvance, isEdit, currentTags } = storeToRefs(topicStore)
|
||||||
|
|
||||||
// 在组件挂载时调用 fetchTopics 获取话题数据(watch 大法好!)
|
// 在组件挂载时调用 fetchTopics 获取话题数据(watch 大法好!)
|
||||||
// watch(
|
// watch(
|
||||||
// [requestData.keywords, requestData.sortField, requestData.sortOrder],
|
// [requestData.keywords, requestData.sortField, requestData.sortOrder],
|
||||||
|
@ -63,28 +59,33 @@ const tid = computed(() => {
|
||||||
|
|
||||||
// 单个话题数据
|
// 单个话题数据
|
||||||
const topicData = ref<TopicDetail>()
|
const topicData = ref<TopicDetail>()
|
||||||
|
|
||||||
// 单个话题的回复数据
|
// 单个话题的回复数据
|
||||||
const repliesData = ref<TopicReply[]>([])
|
const repliesData = ref<TopicReply[]>([])
|
||||||
|
|
||||||
/** 这里拿到的已经是后端返回回来的 data 数据了 */
|
const fetchTopicData = async () => {
|
||||||
onMounted(async () => {
|
|
||||||
// 获取单个话题的数据
|
// 获取单个话题的数据
|
||||||
const topicResponseData = (
|
const topicResponseData = (
|
||||||
await useKUNGalgameTopicStore().getTopicByTid(tid.value)
|
await useKUNGalgameTopicStore().getTopicByTid(tid.value)
|
||||||
).data
|
).data
|
||||||
|
|
||||||
topicData.value = topicResponseData
|
topicData.value = topicResponseData
|
||||||
|
}
|
||||||
|
|
||||||
|
const fetchReplyData = async () => {
|
||||||
// 懒加载获取单个话题下面的回复数据
|
// 懒加载获取单个话题下面的回复数据
|
||||||
const replyResponseData = (
|
const replyResponseData = (
|
||||||
await useKUNGalgameTopicStore().getReplies(tid.value)
|
await useKUNGalgameTopicStore().getReplies(tid.value)
|
||||||
).data
|
).data
|
||||||
repliesData.value = replyResponseData
|
repliesData.value = replyResponseData
|
||||||
})
|
}
|
||||||
|
|
||||||
const { showKUNGalgamePageWidth } = storeToRefs(settingsStore)
|
/** 这里拿到的已经是后端返回回来的 data 数据了 */
|
||||||
const { isShowAdvance, isEdit } = storeToRefs(topicStore)
|
onMounted(async () => {
|
||||||
|
await fetchTopicData()
|
||||||
|
await fetchReplyData()
|
||||||
|
if (topicData.value?.tags) {
|
||||||
|
currentTags.value = topicData.value?.tags
|
||||||
|
}
|
||||||
|
})
|
||||||
|
|
||||||
/* 话题界面的页面宽度 */
|
/* 话题界面的页面宽度 */
|
||||||
const topicPageWidth = computed(() => {
|
const topicPageWidth = computed(() => {
|
||||||
|
@ -115,17 +116,10 @@ onBeforeMount(() => {
|
||||||
<div class="container">
|
<div class="container">
|
||||||
<!-- 下方可视内容区的容器 -->
|
<!-- 下方可视内容区的容器 -->
|
||||||
<div class="content-container">
|
<div class="content-container">
|
||||||
<div class="aside">
|
<!-- 侧边栏 -->
|
||||||
<TopicAsideNav />
|
<Aside />
|
||||||
<TopicOtherTag
|
|
||||||
v-if="topicData?.tags"
|
|
||||||
style="margin-bottom: 17px"
|
|
||||||
:tags="topicData.tags"
|
|
||||||
/>
|
|
||||||
<TopicMaster />
|
|
||||||
<KUNGalgameFooter />
|
|
||||||
</div>
|
|
||||||
|
|
||||||
|
<!-- 内容区 -->
|
||||||
<div class="content">
|
<div class="content">
|
||||||
<Master v-if="topicData" :topicData="topicData" />
|
<Master v-if="topicData" :topicData="topicData" />
|
||||||
<Reply v-if="repliesData" :repliesData="repliesData" />
|
<Reply v-if="repliesData" :repliesData="repliesData" />
|
||||||
|
@ -165,23 +159,6 @@ onBeforeMount(() => {
|
||||||
box-sizing: border-box;
|
box-sizing: border-box;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* 左侧内容区 */
|
|
||||||
.aside {
|
|
||||||
top: 70px;
|
|
||||||
position: sticky;
|
|
||||||
/* 左侧区域的总高度 */
|
|
||||||
height: 940px;
|
|
||||||
/* 左侧区域宽度 */
|
|
||||||
width: 250px;
|
|
||||||
/* 左侧内容区为弹性盒,方便分成上下两部分 */
|
|
||||||
display: flex;
|
|
||||||
flex-shrink: 0;
|
|
||||||
flex-direction: column;
|
|
||||||
box-sizing: border-box;
|
|
||||||
color: var(--kungalgame-font-color-3);
|
|
||||||
margin-right: 5px;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* 右侧内容区 */
|
/* 右侧内容区 */
|
||||||
.content {
|
.content {
|
||||||
height: 100%;
|
height: 100%;
|
||||||
|
|
100
src/views/topic/aside/Aside.vue
Normal file
100
src/views/topic/aside/Aside.vue
Normal file
|
@ -0,0 +1,100 @@
|
||||||
|
<script setup lang="ts">
|
||||||
|
// 导入图标
|
||||||
|
import { Icon } from '@iconify/vue'
|
||||||
|
// 导入 Vue 函数
|
||||||
|
import { ref, watch } from 'vue'
|
||||||
|
import AsideActive from './components/AsideActive.vue'
|
||||||
|
|
||||||
|
import AsideBase from './components/AsideBase.vue'
|
||||||
|
|
||||||
|
// 导入用户 store
|
||||||
|
import { useKUNGalgameHomeStore } from '@/store/modules/home'
|
||||||
|
import { storeToRefs } from 'pinia'
|
||||||
|
|
||||||
|
const { isActiveMainPageAside } = storeToRefs(useKUNGalgameHomeStore())
|
||||||
|
|
||||||
|
const asideWidth = ref('240px')
|
||||||
|
const handleFold = () => {
|
||||||
|
isActiveMainPageAside.value = !isActiveMainPageAside.value
|
||||||
|
}
|
||||||
|
watch(
|
||||||
|
isActiveMainPageAside,
|
||||||
|
() => {
|
||||||
|
asideWidth.value = isActiveMainPageAside.value ? '250px' : '40px'
|
||||||
|
},
|
||||||
|
{ immediate: true }
|
||||||
|
)
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<template>
|
||||||
|
<!-- 侧边栏 -->
|
||||||
|
<div class="aside">
|
||||||
|
<!-- 侧边栏交互 -->
|
||||||
|
<div class="nav-aside" @click="handleFold">
|
||||||
|
<!-- fa 箭头图标字体 -->
|
||||||
|
<Icon
|
||||||
|
icon="line-md:arrow-left"
|
||||||
|
style="font-size: 17px"
|
||||||
|
v-if="isActiveMainPageAside"
|
||||||
|
/>
|
||||||
|
<Icon
|
||||||
|
icon="line-md:arrow-right"
|
||||||
|
style="font-size: 17px"
|
||||||
|
v-if="!isActiveMainPageAside"
|
||||||
|
/>
|
||||||
|
<span v-if="isActiveMainPageAside">{{
|
||||||
|
$tm('mainPage.asideActive.fold')
|
||||||
|
}}</span>
|
||||||
|
</div>
|
||||||
|
<div class="item-active" v-if="isActiveMainPageAside">
|
||||||
|
<AsideActive />
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="item" v-if="!isActiveMainPageAside">
|
||||||
|
<AsideBase :isActive="!isActiveMainPageAside" />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<style lang="scss" scoped>
|
||||||
|
/* 侧边栏部分 */
|
||||||
|
.aside {
|
||||||
|
/* 侧边栏距离文章区域的距离 */
|
||||||
|
margin-right: 5px;
|
||||||
|
width: v-bind('asideWidth');
|
||||||
|
/* 侧边栏相对于整体可视部分的占比 */
|
||||||
|
/* 侧边栏高度 */
|
||||||
|
height: 100%;
|
||||||
|
/* 设置侧边栏为弹性盒子 */
|
||||||
|
display: flex;
|
||||||
|
/* 方向为竖向 */
|
||||||
|
flex-direction: column;
|
||||||
|
transition: 0.5s;
|
||||||
|
span {
|
||||||
|
white-space: nowrap;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/* 侧边栏交互 */
|
||||||
|
.nav-aside {
|
||||||
|
height: 40px;
|
||||||
|
/* 内容居中(折叠左侧区域) */
|
||||||
|
display: flex;
|
||||||
|
flex-shrink: 0;
|
||||||
|
justify-content: center;
|
||||||
|
align-items: center;
|
||||||
|
text-align: center;
|
||||||
|
/* 字体设置 */
|
||||||
|
font-size: small;
|
||||||
|
color: var(--kungalgame-font-color-3);
|
||||||
|
cursor: pointer;
|
||||||
|
}
|
||||||
|
/* 激活后的左侧区域 */
|
||||||
|
.item-active {
|
||||||
|
display: flex;
|
||||||
|
flex-grow: 1;
|
||||||
|
}
|
||||||
|
/* 未激活的左侧区域 */
|
||||||
|
.item {
|
||||||
|
height: 96.6%;
|
||||||
|
}
|
||||||
|
</style>
|
34
src/views/topic/aside/components/AsideActive.vue
Normal file
34
src/views/topic/aside/components/AsideActive.vue
Normal file
|
@ -0,0 +1,34 @@
|
||||||
|
<script setup lang="ts">
|
||||||
|
import TopicAsideNav from './TopicAsideNav.vue'
|
||||||
|
import TopicOtherTag from './TopicOtherTag.vue'
|
||||||
|
import TopicMaster from './TopicMaster.vue'
|
||||||
|
import KUNGalgameFooter from '@/components/KUNGalgameFooter.vue'
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<template>
|
||||||
|
<div class="aside">
|
||||||
|
<TopicAsideNav />
|
||||||
|
<TopicOtherTag style="margin-bottom: 17px" />
|
||||||
|
<TopicMaster />
|
||||||
|
<KUNGalgameFooter />
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<style lang="scss" scoped>
|
||||||
|
/* 左侧内容区 */
|
||||||
|
.aside {
|
||||||
|
top: 70px;
|
||||||
|
position: sticky;
|
||||||
|
/* 左侧区域的总高度 */
|
||||||
|
height: 940px;
|
||||||
|
/* 左侧区域宽度 */
|
||||||
|
width: 100%;
|
||||||
|
/* 左侧内容区为弹性盒,方便分成上下两部分 */
|
||||||
|
display: flex;
|
||||||
|
flex-shrink: 0;
|
||||||
|
flex-direction: column;
|
||||||
|
box-sizing: border-box;
|
||||||
|
color: var(--kungalgame-font-color-3);
|
||||||
|
margin-right: 5px;
|
||||||
|
}
|
||||||
|
</style>
|
11
src/views/topic/aside/components/AsideBase.vue
Normal file
11
src/views/topic/aside/components/AsideBase.vue
Normal file
|
@ -0,0 +1,11 @@
|
||||||
|
<script setup lang='ts'>
|
||||||
|
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<template>
|
||||||
|
<div>AsideBase</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<style lang='scss' scoped>
|
||||||
|
|
||||||
|
</style>
|
|
@ -2,35 +2,32 @@
|
||||||
这里是楼主的其他话题组件
|
这里是楼主的其他话题组件
|
||||||
-->
|
-->
|
||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
import { ref, onMounted, toRaw } from 'vue'
|
import { onMounted, ref, toRaw } from 'vue'
|
||||||
|
import { useRoute } from 'vue-router'
|
||||||
|
|
||||||
import { TopicAside } from '@/api/index'
|
import { TopicAside } from '@/api/index'
|
||||||
|
|
||||||
// 导入 topic store
|
// 导入 topic store
|
||||||
import { useKUNGalgameTopicStore } from '@/store/modules/topic'
|
import { useKUNGalgameTopicStore } from '@/store/modules/topic'
|
||||||
|
// 当前页面的 tags
|
||||||
import { useRoute } from 'vue-router'
|
const tags = useKUNGalgameTopicStore().currentTags
|
||||||
|
// 当前路由实例
|
||||||
const route = useRoute()
|
const route = useRoute()
|
||||||
|
// 当前所在话题的 id
|
||||||
const tid = parseInt(route.params.tid as string)
|
const tid = parseInt(route.params.tid as string)
|
||||||
|
|
||||||
const props = defineProps<{
|
|
||||||
tags: string[]
|
|
||||||
}>()
|
|
||||||
|
|
||||||
const tags = toRaw(props.tags)
|
|
||||||
|
|
||||||
const topicData = ref<TopicAside[]>()
|
const topicData = ref<TopicAside[]>()
|
||||||
|
|
||||||
onMounted(async () => {
|
const fetchTopicData = async () => {
|
||||||
topicData.value = (
|
topicData.value = (
|
||||||
await useKUNGalgameTopicStore().getRelatedTopicsByTags({
|
await useKUNGalgameTopicStore().getRelatedTopicsByTags({
|
||||||
tags: tags,
|
tags: tags,
|
||||||
tid: tid,
|
tid: tid,
|
||||||
})
|
})
|
||||||
).data
|
).data
|
||||||
})
|
}
|
||||||
|
|
||||||
|
fetchTopicData()
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<template>
|
<template>
|
Loading…
Reference in a new issue