|
@@ -49,18 +49,52 @@
|
|
|
</ul>
|
|
|
<p v-else style="text-align: center">暂无批注</p>
|
|
|
</div>
|
|
|
-
|
|
|
- <div class="sidebar">
|
|
|
+ <div ref="sidebarMenu" class="sidebar">
|
|
|
<div
|
|
|
- v-for="{ icon, title, handle } in sidebarIconList"
|
|
|
- :key="icon"
|
|
|
- :title="title"
|
|
|
+ v-for="item in sidebarIconList"
|
|
|
+ :key="item.icon"
|
|
|
+ :title="item.title"
|
|
|
class="sidebar-icon"
|
|
|
- @click="handleSidebarClick(handle)"
|
|
|
+ @click="handleSidebarClick(item)"
|
|
|
>
|
|
|
- <SvgIcon :icon-class="`sidebar-${icon}`" size="24" />
|
|
|
+ <SvgIcon :icon-class="`sidebar-${item.icon}`" size="24" />
|
|
|
</div>
|
|
|
</div>
|
|
|
+ <el-drawer
|
|
|
+ custom-class="custom-drawer"
|
|
|
+ :visible="drawerType.length > 0"
|
|
|
+ :with-header="false"
|
|
|
+ :modal="false"
|
|
|
+ size="25%"
|
|
|
+ :style="drawerStyle"
|
|
|
+ >
|
|
|
+ <div class="infinite-list-wrapper" style="overflow: auto">
|
|
|
+ <ul v-infinite-scroll="loadMore" class="scroll-container" infinite-scroll-disabled="disabled">
|
|
|
+ <li
|
|
|
+ v-for="(item, index) in file_list"
|
|
|
+ :key="index"
|
|
|
+ class="list-item"
|
|
|
+ @click="handleFileClick(item?.component_id)"
|
|
|
+ >
|
|
|
+ <template v-if="parseInt(drawerType) === 0"> <el-image :src="item.file_url" fit="contain" /></template>
|
|
|
+ <template v-else-if="parseInt(drawerType) === 1">
|
|
|
+ <AudioPlay
|
|
|
+ view-size="middle"
|
|
|
+ :file-id="item.file_id"
|
|
|
+ :file-name="item.file_name.slice(0, item.file_name.lastIndexOf('.'))"
|
|
|
+ :show-slider="true"
|
|
|
+ :audio-index="index"
|
|
|
+ />
|
|
|
+ </template>
|
|
|
+ <template v-else-if="parseInt(drawerType) === 2">
|
|
|
+ <VideoPlay view-size="big" :file-id="item.file_id" :video-index="index" />
|
|
|
+ </template>
|
|
|
+ </li>
|
|
|
+ </ul>
|
|
|
+ <p v-if="loading">加载中...</p>
|
|
|
+ <p v-if="noMore">没有更多了</p>
|
|
|
+ </div>
|
|
|
+ </el-drawer>
|
|
|
</div>
|
|
|
|
|
|
<el-dialog
|
|
@@ -104,6 +138,8 @@ import MenuPopover from '@/views/personal_workbench/common/MenuPopover.vue';
|
|
|
import RichText from '@/components/RichText.vue';
|
|
|
import { isTrue } from '@/utils/common';
|
|
|
import MindMap from '@/components/MindMap.vue';
|
|
|
+import VideoPlay from '@/views/book/courseware/preview/components/common/VideoPlay.vue';
|
|
|
+import AudioPlay from '@/views/book/courseware/preview/components/common/AudioPlay.vue';
|
|
|
|
|
|
import {
|
|
|
GetBookCoursewareInfo,
|
|
@@ -117,6 +153,7 @@ import {
|
|
|
ChapterGetBookChapterStructExpandList,
|
|
|
GetBookBaseInfo,
|
|
|
MangerGetBookMindMap,
|
|
|
+ PageQueryBookResourceList,
|
|
|
} from '@/api/book';
|
|
|
|
|
|
export default {
|
|
@@ -126,6 +163,8 @@ export default {
|
|
|
MenuPopover,
|
|
|
RichText,
|
|
|
MindMap,
|
|
|
+ AudioPlay,
|
|
|
+ VideoPlay,
|
|
|
},
|
|
|
props: {
|
|
|
projectId: {
|
|
@@ -191,9 +230,9 @@ export default {
|
|
|
{ icon: 'search', title: '搜索', handle: '' },
|
|
|
{ icon: 'mindmap', title: '思维导图', handle: 'openMindMap' },
|
|
|
{ icon: 'connect', title: '连接', handle: '' },
|
|
|
- { icon: 'audio', title: '音频', handle: '' },
|
|
|
- { icon: 'image', title: '图片', handle: '' },
|
|
|
- { icon: 'video', title: '视频', handle: '' },
|
|
|
+ { icon: 'audio', title: '音频', handle: 'openDrawer', type: '1' },
|
|
|
+ { icon: 'image', title: '图片', handle: 'openDrawer', type: '0' },
|
|
|
+ { icon: 'video', title: '视频', handle: 'openDrawer', type: '2' },
|
|
|
{ icon: 'text', title: '文本', handle: '' },
|
|
|
{ icon: 'collect', title: '收藏', handle: '' },
|
|
|
{ icon: 'setting', title: '设置', handle: '' },
|
|
@@ -201,8 +240,27 @@ export default {
|
|
|
visibleMindMap: false,
|
|
|
isChildDataLoad: false,
|
|
|
mindMapJsonData: {}, // 思维导图json数据
|
|
|
+ drawerType: '', // 抽屉类型
|
|
|
+ drawerStyle: {
|
|
|
+ top: '0',
|
|
|
+ height: '0',
|
|
|
+ right: '0',
|
|
|
+ },
|
|
|
+ page_capacity: 10,
|
|
|
+ cur_page: 1,
|
|
|
+ file_list: [],
|
|
|
+ total_count: 0,
|
|
|
+ loading: false,
|
|
|
};
|
|
|
},
|
|
|
+ computed: {
|
|
|
+ disabled() {
|
|
|
+ return this.loading || this.noMore;
|
|
|
+ },
|
|
|
+ noMore() {
|
|
|
+ return this.file_list.length >= this.total_count && this.total_count > 0;
|
|
|
+ },
|
|
|
+ },
|
|
|
created() {
|
|
|
if (this.id) {
|
|
|
this.getBookCoursewareInfo(this.id);
|
|
@@ -213,6 +271,9 @@ export default {
|
|
|
}
|
|
|
this.getBookChapterStructExpandList();
|
|
|
},
|
|
|
+ mounted() {
|
|
|
+ this.calcDrawerPosition();
|
|
|
+ },
|
|
|
methods: {
|
|
|
getProjectBaseInfo() {
|
|
|
GetProjectBaseInfo({ id: this.projectId }).then(({ project_info }) => {
|
|
@@ -361,11 +422,16 @@ export default {
|
|
|
* @param {string} handle - 处理函数名
|
|
|
* @param {any} param - 处理函数参数
|
|
|
*/
|
|
|
- handleSidebarClick(handle, param) {
|
|
|
- if (typeof handle === 'string' && handle && typeof this[handle] === 'function') {
|
|
|
- this[handle](param);
|
|
|
+ handleSidebarClick(item) {
|
|
|
+ let handle = item.handle;
|
|
|
+ if (typeof this[handle] === 'function') {
|
|
|
+ this[handle](item.type);
|
|
|
}
|
|
|
+ // if (typeof handle === 'string' && handle && typeof this[handle] === 'function') {
|
|
|
+ // this[handle](param);
|
|
|
+ // }
|
|
|
},
|
|
|
+
|
|
|
openMindMap() {
|
|
|
MangerGetBookMindMap({ book_id: this.projectId }).then(({ content }) => {
|
|
|
if (content) {
|
|
@@ -392,6 +458,66 @@ export default {
|
|
|
}
|
|
|
this.visibleMindMap = false;
|
|
|
},
|
|
|
+
|
|
|
+ // 计算抽屉滑出位置
|
|
|
+ calcDrawerPosition() {
|
|
|
+ const menu = this.$refs.sidebarMenu;
|
|
|
+ if (menu) {
|
|
|
+ const rect = menu.getBoundingClientRect();
|
|
|
+ this.drawerStyle = {
|
|
|
+ top: `${rect.top}px`,
|
|
|
+ height: `${rect.height}px`,
|
|
|
+ right: `${window.innerWidth - rect.left + 1}px`,
|
|
|
+ };
|
|
|
+ }
|
|
|
+ },
|
|
|
+ // 打开抽屉并初始化加载
|
|
|
+ openDrawer(type) {
|
|
|
+ if (this.drawerType === type) {
|
|
|
+ this.drawerType = '';
|
|
|
+ return;
|
|
|
+ }
|
|
|
+ this.drawerType = type;
|
|
|
+ this.drawerVisible = true;
|
|
|
+ this.$nextTick(() => {
|
|
|
+ this.cur_page = 1;
|
|
|
+ this.file_list = [];
|
|
|
+ this.loadMore();
|
|
|
+ });
|
|
|
+ },
|
|
|
+ // 加载更多数据
|
|
|
+ loadMore() {
|
|
|
+ if (this.disabled) return;
|
|
|
+ this.loading = true;
|
|
|
+ const params = {
|
|
|
+ page_capacity: this.page_capacity,
|
|
|
+ cur_page: this.cur_page,
|
|
|
+ book_id: this.projectId,
|
|
|
+ type: parseInt(this.drawerType),
|
|
|
+ };
|
|
|
+ PageQueryBookResourceList(params)
|
|
|
+ .then(({ total_count, resource_list }) => {
|
|
|
+ this.total_count = total_count;
|
|
|
+ this.file_list = this.cur_page === 1 ? resource_list : [...this.file_list, ...resource_list];
|
|
|
+ this.cur_page += this.cur_page;
|
|
|
+ })
|
|
|
+ .finally(() => {
|
|
|
+ this.loading = false;
|
|
|
+ });
|
|
|
+ },
|
|
|
+ async handleFileClick(component_id) {
|
|
|
+ if (component_id) {
|
|
|
+ let node = await this.$refs.courserware.findChildComponentByKey(component_id);
|
|
|
+ if (node) {
|
|
|
+ await this.$nextTick();
|
|
|
+ this.$refs.previewMain.scrollTo({
|
|
|
+ top: node.offsetTop - 50,
|
|
|
+ left: node.offsetLeft - 50,
|
|
|
+ behavior: 'smooth',
|
|
|
+ });
|
|
|
+ }
|
|
|
+ }
|
|
|
+ },
|
|
|
},
|
|
|
};
|
|
|
</script>
|
|
@@ -571,6 +697,52 @@ export default {
|
|
|
cursor: pointer;
|
|
|
}
|
|
|
}
|
|
|
+
|
|
|
+ .el-drawer__body {
|
|
|
+ .scroll-container {
|
|
|
+ display: flex;
|
|
|
+ flex-direction: column;
|
|
|
+ row-gap: 8px;
|
|
|
+ margin: 6px;
|
|
|
+
|
|
|
+ .list-item {
|
|
|
+ cursor: pointer;
|
|
|
+ border: 1px solid #ccc;
|
|
|
+ border-radius: 8px;
|
|
|
+
|
|
|
+ :deep .el-slider {
|
|
|
+ .el-slider__runway {
|
|
|
+ background-color: #eee;
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ :deep .audio-middle {
|
|
|
+ width: 100%;
|
|
|
+ border: none;
|
|
|
+ border-radius: 8px;
|
|
|
+ }
|
|
|
+
|
|
|
+ .el-image {
|
|
|
+ display: flex;
|
|
|
+ width: 30%;
|
|
|
+ height: 90px;
|
|
|
+ margin: 6px;
|
|
|
+ background-color: #ccc;
|
|
|
+ border-radius: 8px;
|
|
|
+ }
|
|
|
+
|
|
|
+ .video-play {
|
|
|
+ width: 30%;
|
|
|
+ margin: 6px;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ p {
|
|
|
+ color: #999;
|
|
|
+ text-align: center;
|
|
|
+ }
|
|
|
+ }
|
|
|
}
|
|
|
}
|
|
|
|