index.tsx 14 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415
  1. import {
  2. PropType,
  3. defineComponent,
  4. nextTick,
  5. onMounted,
  6. reactive,
  7. ref,
  8. toRef
  9. } from 'vue';
  10. import styles from './index.module.less';
  11. import {
  12. NButton,
  13. NForm,
  14. NFormItem,
  15. NImage,
  16. NPopselect,
  17. NSpace
  18. } from 'naive-ui';
  19. import { resourceTypeArray } from '/src/utils/searchArray';
  20. import { useCatchStore } from '/src/store/modules/catchData';
  21. import { useThrottleFn } from '@vueuse/core';
  22. import TheSearch from '/src/components/TheSearch';
  23. import isCollaose from '/src/views/natural-resources/images/isCollaose.png';
  24. export default defineComponent({
  25. name: 'resource-search-group',
  26. props: {
  27. type: {
  28. type: String as PropType<
  29. 'relateResources' | 'shareResources' | 'myResources' | 'myCollect'
  30. >,
  31. default: 'shareResources'
  32. },
  33. subjectId: {
  34. type: String,
  35. default: null
  36. }
  37. },
  38. emits: ['search'],
  39. setup(props, { emit }) {
  40. const subjectId = toRef(props.subjectId);
  41. const catchStore = useCatchStore();
  42. const forms = reactive({
  43. type: 'MUSIC', //
  44. name: '',
  45. subjectId: subjectId.value as any,
  46. grade: null as any,
  47. bookVersionId: null as any,
  48. musicSheetCategoriesId: null as any
  49. });
  50. const state = reactive({
  51. tempSubjectId: null,
  52. gradeList: [] as any[],
  53. musicCategory: [] as any
  54. });
  55. const resourceType = ref([] as any);
  56. const onSearch = (type?: string) => {
  57. emit('search', forms, type);
  58. };
  59. const throttleFn = useThrottleFn(() => onSearch(), 500);
  60. const collapseWrapRef = ref();
  61. const divDomList = ref([] as any);
  62. const orginHeight = ref(0);
  63. const hiddenHeight = ref(0);
  64. const line = ref(0);
  65. const isCollapse = ref(false);
  66. const loadingCollapse = ref(false); // 是否加载完成
  67. const musicCateRef = (el: any) => {
  68. if (el?.selfElRef) {
  69. divDomList.value.push(el.selfElRef.parentNode);
  70. }
  71. };
  72. const setCollapse = (flag: boolean) => {
  73. isCollapse.value = flag;
  74. getLive();
  75. };
  76. const getLive = () => {
  77. try {
  78. divDomList.value = [...new Set(divDomList.value)];
  79. let offsetLeft = -1;
  80. divDomList.value.forEach((item: any, index: number) => {
  81. if (index === 0) {
  82. line.value = 1;
  83. offsetLeft = item.offsetLeft;
  84. } else if (item.offsetLeft === offsetLeft && index != 0) {
  85. // 如果某个标签的offsetLeft和第一个标签的offsetLeft相等 说明增加了一行
  86. line.value++;
  87. }
  88. if (!isCollapse.value) {
  89. if (line.value > 1) {
  90. //从第3行开始 隐藏标签
  91. item.style.display = 'none';
  92. // 显示展开按钮 class名chu是在前面动态添加的
  93. } else {
  94. item.style.display = 'block';
  95. }
  96. } else {
  97. item.style.display = 'block';
  98. }
  99. });
  100. loadingCollapse.value = true;
  101. } catch {
  102. //
  103. }
  104. };
  105. const selectChildObj = (item: any) => {
  106. const obj: any = {};
  107. item?.forEach((child: any) => {
  108. if (child.id === forms.subjectId) {
  109. obj.selected = true;
  110. obj.name = child.name;
  111. }
  112. });
  113. return obj;
  114. };
  115. const onChangeSearch = (type: string, list: any) => {
  116. if (type === 'version') {
  117. console.log(list, 'list');
  118. state.gradeList = list || [];
  119. if (state.gradeList.length > 0) {
  120. forms.grade = state.gradeList[0].id;
  121. state.musicCategory = state.gradeList[0].children || [];
  122. if (state.musicCategory.length > 0) {
  123. forms.musicSheetCategoriesId = state.musicCategory[0].id;
  124. } else {
  125. forms.musicSheetCategoriesId = null;
  126. }
  127. } else {
  128. state.musicCategory = [] as any;
  129. }
  130. } else if (type === 'grade') {
  131. state.musicCategory = list || [];
  132. if (state.musicCategory.length > 0) {
  133. forms.musicSheetCategoriesId = state.musicCategory[0].id;
  134. } else {
  135. forms.musicSheetCategoriesId = null;
  136. }
  137. }
  138. };
  139. onMounted(async () => {
  140. // if (props.type === 'myCollect') {
  141. // resourceType.value.push({
  142. // label: '全部',
  143. // value: ''
  144. // });
  145. // forms.type = ''; // 默认全部
  146. // }
  147. resourceTypeArray.forEach((item: any) => {
  148. // if (props.type === 'myResources') {
  149. // item.value !== 'MUSIC' && resourceType.value.push(item);
  150. // } else {
  151. resourceType.value.push(item);
  152. // }
  153. });
  154. // // 获取教材分类列表
  155. // await catchStore.getMusicSheetCategory();
  156. await catchStore.getMusicTagTreeApi();
  157. // 获取声部
  158. await catchStore.getSubjects();
  159. // console.log(
  160. // catchStore.getSubjectInstruments,
  161. // 'catchStore.getSubjectInstruments'
  162. // );
  163. // catchStore.getSubjectInstruments.forEach((item: any) => {
  164. // if (item.id == props.subjectId && Array.isArray(item.instruments)) {
  165. // if (item.instruments.length > 0) {
  166. // forms.subjectId = item.instruments[0].value;
  167. // } else {
  168. // forms.subjectId = item.value;
  169. // }
  170. // }
  171. // });
  172. forms.subjectId = null;
  173. // 这里开始
  174. // musicCateRef
  175. if (forms.type === 'MUSIC') {
  176. orginHeight.value = collapseWrapRef.value?.offsetHeight;
  177. hiddenHeight.value = collapseWrapRef.value?.offsetHeight / line.value;
  178. // 默认隐藏
  179. getLive();
  180. const musicTagTreeList = catchStore.getMusicTagTree;
  181. if (musicTagTreeList.length > 0) {
  182. forms.bookVersionId = musicTagTreeList[0].id;
  183. state.gradeList = musicTagTreeList[0].children || [];
  184. if (state.gradeList.length > 0) {
  185. forms.grade = state.gradeList[0].id;
  186. state.musicCategory = state.gradeList[0].children || [];
  187. if (state.musicCategory.length > 0) {
  188. forms.musicSheetCategoriesId = state.musicCategory[0].id;
  189. }
  190. }
  191. }
  192. }
  193. if (props.type === 'shareResources') {
  194. onSearch('timer');
  195. }
  196. });
  197. return () => (
  198. <div class={styles.searchGroup}>
  199. <div class={styles.searchCatatory}>
  200. <NSpace size="small" class={styles.btnType}>
  201. {resourceType.value.map((item: any) => (
  202. <NButton
  203. type={forms.type === item.value ? 'primary' : 'default'}
  204. secondary={forms.type === item.value ? false : true}
  205. round
  206. size="small"
  207. focusable={false}
  208. onClick={() => {
  209. forms.type = item.value;
  210. forms.subjectId = null;
  211. onSearch();
  212. try {
  213. nextTick(() => {
  214. if (forms.type === 'MUSIC') {
  215. orginHeight.value = collapseWrapRef.value?.offsetHeight;
  216. hiddenHeight.value =
  217. collapseWrapRef.value?.offsetHeight / line.value;
  218. // 默认隐藏
  219. getLive();
  220. } else {
  221. divDomList.value = [];
  222. }
  223. });
  224. } catch {
  225. //
  226. }
  227. }}>
  228. {item.label}
  229. </NButton>
  230. ))}
  231. </NSpace>
  232. <TheSearch
  233. class={styles.inputSearch}
  234. round
  235. onSearch={(val: string) => {
  236. forms.name = val;
  237. throttleFn();
  238. }}
  239. />
  240. </div>
  241. <NForm labelAlign="left" labelPlacement="left">
  242. {forms.type === 'MUSIC' && props.type === 'shareResources' && (
  243. <>
  244. <NFormItem label="版本:">
  245. <NSpace class={styles.spaceSection}>
  246. {catchStore.getMusicTagTree.map((subject: any) => (
  247. <span
  248. class={[
  249. styles.textBtn,
  250. forms.bookVersionId === subject.id &&
  251. styles.textBtnActive
  252. ]}
  253. onClick={() => {
  254. forms.bookVersionId = subject.id;
  255. onChangeSearch('version', subject.children || []);
  256. onSearch();
  257. }}>
  258. {subject.name}
  259. </span>
  260. ))}
  261. </NSpace>
  262. </NFormItem>
  263. {state.gradeList.length > 0 && (
  264. <NFormItem label="年级:">
  265. <NSpace class={styles.spaceSection}>
  266. {state.gradeList.map((subject: any) => (
  267. <span
  268. class={[
  269. styles.textBtn,
  270. forms.grade === subject.id && styles.textBtnActive
  271. ]}
  272. onClick={() => {
  273. forms.grade = subject.id;
  274. onChangeSearch('grade', subject.children || []);
  275. onSearch();
  276. }}>
  277. {subject.name}
  278. </span>
  279. ))}
  280. </NSpace>
  281. </NFormItem>
  282. )}
  283. {state.musicCategory.length > 0 && (
  284. <div class={styles.collapsSection}>
  285. <NFormItem label="教材:">
  286. <div
  287. class={[
  288. styles.collapseWrap,
  289. loadingCollapse.value ? '' : styles.hideButton,
  290. isCollapse.value ? '' : styles.isHidden
  291. ]}
  292. ref={collapseWrapRef}>
  293. <NSpace class={[styles.spaceSection]}>
  294. {state.musicCategory.map((music: any) => (
  295. <NButton
  296. ref={musicCateRef}
  297. secondary={
  298. forms.musicSheetCategoriesId === music.id
  299. }
  300. quaternary={
  301. forms.musicSheetCategoriesId !== music.id
  302. }
  303. strong
  304. focusable={false}
  305. type={
  306. forms.musicSheetCategoriesId === music.id
  307. ? 'primary'
  308. : 'default'
  309. }
  310. onClick={() => {
  311. forms.musicSheetCategoriesId = music.id;
  312. onSearch();
  313. }}>
  314. {music.name}
  315. </NButton>
  316. ))}
  317. {line.value > 1 && (
  318. <div
  319. class={styles.collaoseGroup}
  320. onClick={() => {
  321. setCollapse(!isCollapse.value);
  322. }}>
  323. <NImage
  324. previewDisabled
  325. src={isCollaose}
  326. class={[
  327. styles.collaoseBtn,
  328. isCollapse.value ? styles.isStart : ''
  329. ]}></NImage>
  330. </div>
  331. )}
  332. </NSpace>
  333. </div>
  334. </NFormItem>
  335. </div>
  336. )}
  337. </>
  338. )}
  339. <NFormItem label="乐器:">
  340. <NSpace class={styles.spaceSection2}>
  341. {/* {catchStore.getSubjectAllList.map((music: any) => (
  342. <NButton
  343. secondary={forms.subjectId === music.id}
  344. quaternary={forms.subjectId !== music.id}
  345. strong
  346. focusable={false}
  347. type={forms.subjectId === music.id ? 'primary' : 'default'}
  348. onClick={() => {
  349. forms.subjectId = music.id;
  350. onSearch();
  351. }}>
  352. {music.name}
  353. </NButton>
  354. ))} */}
  355. {catchStore.getSubjectInstruments.map((subject: any) =>
  356. subject.instruments && subject.instruments.length > 1 ? (
  357. <NPopselect
  358. options={subject.instruments}
  359. trigger="hover"
  360. scrollable
  361. v-model:value={state.tempSubjectId}
  362. onUpdate:value={() => {
  363. forms.subjectId = state.tempSubjectId;
  364. onSearch();
  365. }}
  366. key={subject.value}
  367. class={[styles.popSelect]}>
  368. <span
  369. class={[
  370. styles.textBtn,
  371. selectChildObj(subject.instruments).selected &&
  372. styles.textBtnActive
  373. ]}>
  374. {selectChildObj(subject.instruments).name || subject.name}
  375. <i class={styles.iconArrow}></i>
  376. </span>
  377. </NPopselect>
  378. ) : (
  379. <span
  380. class={[
  381. styles.textBtn,
  382. forms.subjectId === subject.value && styles.textBtnActive
  383. ]}
  384. onClick={() => {
  385. forms.subjectId = subject.value;
  386. state.tempSubjectId = null;
  387. onSearch();
  388. }}>
  389. {subject.name}
  390. </span>
  391. )
  392. )}
  393. </NSpace>
  394. </NFormItem>
  395. </NForm>
  396. </div>
  397. );
  398. }
  399. });