index.vue 7.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307
  1. <template>
  2. <div ref="create" class="create">
  3. <div class="create-left">
  4. <div class="back-container">
  5. <el-button class="back" @click="judgeIsHasChange"><i class="el-icon-arrow-left"></i> 返回</el-button>
  6. <span class="title">Frame {{ Number(index) + 1 }}</span>
  7. </div>
  8. <div v-for="{ value, label, children } in bookTypeOption" :key="value" class="components">
  9. <div class="components-title">{{ label }}</div>
  10. <div
  11. v-for="{ value: childValue, icon, label: childLabel } in children"
  12. :key="childValue"
  13. ref="componentsItem"
  14. class="components-item"
  15. @mousedown="dragStart($event, childValue)"
  16. >
  17. <SvgIcon v-if="icon" :icon-class="icon" />
  18. <span>{{ childLabel }}</span>
  19. </div>
  20. </div>
  21. </div>
  22. <div class="create-middle">
  23. <div class="create-operation">
  24. <el-button @click="showSetBackground"><SvgIcon icon-class="background-img" />背景图</el-button>
  25. <el-button><SvgIcon icon-class="template" />模板</el-button>
  26. <el-button class="exit-edit">
  27. <span @click="saveCoursewareContent('edit')">
  28. <template v-if="isEdit"> <i class="el-icon-close"></i><span> 退出编辑</span> </template>
  29. <template v-else> <i class="el-icon-edit"></i><span> 编辑</span> </template>
  30. </span>
  31. <el-button class="save" type="primary">
  32. <span @click="saveCoursewareContent"><SvgIcon icon-class="save" /> <span>保存</span></span>
  33. <el-popover placement="bottom" popper-class="save-popover" trigger="click">
  34. <div class="save-template">保存为模板</div>
  35. <i slot="reference" class="el-icon-arrow-down"></i>
  36. </el-popover>
  37. </el-button>
  38. </el-button>
  39. </div>
  40. <CreateCanvas
  41. ref="createCanvas"
  42. :is-edit="isEdit"
  43. @showSetting="showSetting"
  44. @showSettingEmpty="showSettingEmpty"
  45. @changeData="changeData"
  46. @back="back"
  47. @changeEditStatus="changeEditStatus"
  48. />
  49. </div>
  50. <div class="create-right">
  51. <div class="setting-tittle">设置</div>
  52. <component :is="componentSettingList[curSettingType]" ref="setting" />
  53. </div>
  54. <SelectBackground :visible.sync="visible" @setBackgroundImage="setBackgroundImage" />
  55. <WarnSave :visible.sync="visibleWarn" @directQuit="back" @saveAndClose="saveCoursewareContent" />
  56. </div>
  57. </template>
  58. <script>
  59. import { bookTypeOption, componentSettingList } from '../data/bookType';
  60. import CreateCanvas from './components/createCanvas.vue';
  61. import SelectBackground from './components/SelectBackground.vue';
  62. import WarnSave from './components/WarnSave.vue';
  63. export default {
  64. name: 'CreatePage',
  65. components: {
  66. CreateCanvas,
  67. SelectBackground,
  68. WarnSave,
  69. },
  70. provide() {
  71. return {
  72. getCurSettingId: () => this.curSettingId,
  73. courseware_id: this.courseware_id,
  74. };
  75. },
  76. data() {
  77. const { book_id, chapter_id, index } = this.$route.query;
  78. return {
  79. courseware_id: this.$route.params.courseware_id,
  80. book_id,
  81. index,
  82. chapter_id,
  83. curSettingType: '',
  84. curSettingId: '',
  85. componentSettingList,
  86. bookTypeOption,
  87. visible: false,
  88. visibleWarn: false,
  89. isEdit: true, // 是否编辑状态
  90. isChange: false, // 是否有改动
  91. };
  92. },
  93. methods: {
  94. judgeIsHasChange() {
  95. if (this.isChange) {
  96. this.visibleWarn = true;
  97. return;
  98. }
  99. this.back();
  100. },
  101. back() {
  102. this.$router.push({ path: '/chapter', query: { chapter_id: this.chapter_id, book_id: this.book_id } });
  103. },
  104. /**
  105. * 切换编辑状态
  106. */
  107. changeEditStatus() {
  108. this.isEdit = !this.isEdit;
  109. },
  110. dragStart(event, type) {
  111. this.$refs.createCanvas.dragStart(event, type);
  112. },
  113. changeData() {
  114. this.isChange = true;
  115. },
  116. /**
  117. * 保存课件内容
  118. * @param {string} type 是否退出
  119. */
  120. saveCoursewareContent(type = '') {
  121. if (type === 'edit') {
  122. this.curSettingType = '';
  123. this.curSettingId = '';
  124. }
  125. if (type === 'edit' && !this.isChange) {
  126. this.changeEditStatus();
  127. return;
  128. }
  129. this.$refs.createCanvas.saveCoursewareContent(type);
  130. this.isChange = false;
  131. },
  132. showSetBackground() {
  133. this.visible = true;
  134. },
  135. // 显示设置置空
  136. showSettingEmpty() {
  137. this.curSettingType = '';
  138. this.curSettingId = '';
  139. },
  140. /**
  141. * 显示设置
  142. * @param {object} setting 组件设置
  143. * @param {string} type 组件类型
  144. * @param {string} id 组件id
  145. * @param {object} params 组件参数
  146. */
  147. showSetting(setting, type, id, params = {}) {
  148. this.curSettingType = type;
  149. this.curSettingId = id;
  150. this.$nextTick(() => {
  151. this.$refs.setting.setSetting(setting, params);
  152. });
  153. },
  154. setBackgroundImage(...data) {
  155. this.$refs.createCanvas.setBackgroundImage(...data);
  156. },
  157. getRichTextContent() {
  158. return this.$refs.createCanvas.getRichTextContent();
  159. },
  160. },
  161. };
  162. </script>
  163. <style lang="scss" scoped>
  164. .create {
  165. display: flex;
  166. height: 100%;
  167. &-left {
  168. display: flex;
  169. flex-direction: column;
  170. width: 180px;
  171. overflow: auto;
  172. background-color: #fff;
  173. .back-container {
  174. display: flex;
  175. flex-direction: column;
  176. row-gap: 8px;
  177. padding: 4px;
  178. .back {
  179. color: #000;
  180. text-align: left;
  181. background-color: #f4f4f4;
  182. }
  183. .title {
  184. padding: 0 16px;
  185. font-size: 14px;
  186. font-weight: bold;
  187. }
  188. }
  189. .components {
  190. display: flex;
  191. flex-direction: column;
  192. padding: 24px 8px 4px;
  193. margin-top: 12px;
  194. border-top: 1px solid #e5e6eb;
  195. .components-title {
  196. padding-left: 8px;
  197. font-size: 14px;
  198. font-weight: bold;
  199. color: #999;
  200. }
  201. .components-item {
  202. display: flex;
  203. align-items: center;
  204. padding: 5px 16px;
  205. cursor: pointer;
  206. svg {
  207. width: 16px;
  208. height: 16px;
  209. margin-right: 8px;
  210. }
  211. }
  212. }
  213. }
  214. &-middle {
  215. flex: 1;
  216. padding: 24px 20px;
  217. overflow: auto;
  218. background-color: #ececec;
  219. .create-operation {
  220. display: flex;
  221. column-gap: 6px;
  222. align-items: center;
  223. justify-content: center;
  224. margin-bottom: 16px;
  225. .exit-edit {
  226. padding: 4px 4px 4px 16px;
  227. }
  228. > .el-button {
  229. height: 40px;
  230. font-size: 16px;
  231. font-weight: bold;
  232. :deep > span {
  233. display: flex;
  234. column-gap: 8px;
  235. align-items: center;
  236. }
  237. .save.el-button {
  238. height: 32px;
  239. margin-left: 8px;
  240. font-size: 16px;
  241. :deep > span {
  242. display: flex;
  243. column-gap: 4px;
  244. align-items: center;
  245. margin-top: -1px;
  246. }
  247. }
  248. }
  249. }
  250. }
  251. &-right {
  252. width: 280px;
  253. padding: 16px 8px;
  254. background-color: #fff;
  255. .setting-tittle {
  256. margin-bottom: 16px;
  257. font-weight: bold;
  258. color: #000;
  259. }
  260. }
  261. }
  262. </style>
  263. <style lang="scss">
  264. .save-popover {
  265. width: 100px;
  266. min-width: 100px;
  267. padding: 4px;
  268. .save-template {
  269. padding: 4px 8px;
  270. text-align: center;
  271. cursor: pointer;
  272. &:hover {
  273. background-color: #f1f1f1;
  274. }
  275. }
  276. }
  277. </style>