leftMenu.vue 7.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245
  1. <template>
  2. <section class="left-menu" :class="[shortType ? 'short' : '']">
  3. <div class="left-menu-user">
  4. <h1 class="logo"><span style="cursor: pointer" @click="fnMoveHome()">P5G</span></h1>
  5. <div class="user">
  6. <i class="ico"></i>
  7. <span class="type">{{ useAuthStore().getAccountId }}</span>
  8. <!-- <span class="name">{{ useAuthStore().getAccountName }}</span> -->
  9. </div>
  10. </div>
  11. <nav class="left-navi">
  12. <ul class="depth1" v-if="shortType == false">
  13. <li
  14. v-for="(item, index) in arrMenuLists"
  15. :key="index"
  16. :id="'menu_' + item.menu_seq"
  17. :class="item.menu_url.indexOf(currentTopMenuLocation) > -1 ? 'active' : ''"
  18. >
  19. <span class="menu-name" @click="fnMenuEvent(item)"
  20. ><i :class="'ico ico' + (index + 1)"></i>{{ item.menu_nm }}</span
  21. >
  22. <div
  23. class="depth2"
  24. :style="
  25. item.menu_url.indexOf(currentTopMenuLocation) > -1
  26. ? 'display: block'
  27. : 'display: none'
  28. "
  29. >
  30. <ul>
  31. <li
  32. v-for="(itemSub, indexSub) in item.sub"
  33. :key="indexSub"
  34. @click="fnMenuEvent(itemSub)"
  35. :class="currentMenuLocation == itemSub.menu_url ? 'active' : ''"
  36. >
  37. {{ itemSub.menu_nm }}
  38. </li>
  39. </ul>
  40. </div>
  41. </li>
  42. </ul>
  43. <!-- <ul class="depth1" v-else>
  44. <li v-for="(item, index) in arrMenuLists" :key="index" :id="'menu_'+item.menu_seq" :class="item.menu_url.indexOf(currentTopMenuLocation) > -1 ? 'active' : ''">
  45. <span class="menu-name" @click="focusIn(index)"><i :class="'ico ico'+(index+1)"></i></span>
  46. <div class="depth2">
  47. <strong>{{item.menu_nm}}</strong>
  48. <ul>
  49. <li v-for="(itemSub, indexSub) in item.sub" :key="indexSub" @click="fnMenuEvent(itemSub)" :class="currentMenuLocation == itemSub.menu_url ? 'active' : ''">{{itemSub.menu_nm}}</li>
  50. </ul>
  51. </div>
  52. </li>
  53. </ul> -->
  54. <ul class="depth1" v-else>
  55. <li
  56. v-for="(item, index) in arrMenuLists"
  57. style="width: 62px"
  58. :key="index"
  59. @mouseover="focusIn(index)"
  60. @mouseleave="twoDept = null"
  61. :id="'menu_' + item.menu_seq"
  62. :class="item.menu_url.indexOf(currentTopMenuLocation) > -1 ? 'active' : ''"
  63. >
  64. <span class="menu-name"><i :class="'ico ico' + (index + 1)"></i></span>
  65. <div
  66. v-if="twoDept == index"
  67. class="depth2"
  68. @mouseover="focusIn(index)"
  69. style="display: block"
  70. >
  71. <strong>{{ item.menu_nm }}</strong>
  72. <ul>
  73. <li
  74. v-for="(itemSub, indexSub) in item.sub"
  75. :key="indexSub"
  76. @click="fnMenuEvent(itemSub)"
  77. :class="currentMenuLocation == itemSub.menu_url ? 'active' : ''"
  78. >
  79. {{ itemSub.menu_nm }}
  80. </li>
  81. </ul>
  82. </div>
  83. </li>
  84. </ul>
  85. </nav>
  86. <div class="left-btm">
  87. <v-btn
  88. class="custom-btn btn-white"
  89. v-if="shortType == false"
  90. @click="logoutPop = true"
  91. >로그아웃</v-btn
  92. >
  93. <button
  94. style="visibility: hidden"
  95. class="btn-logout"
  96. v-else
  97. @click="logoutPop = true"
  98. ></button>
  99. <v-btn
  100. class="custom-btn btn-white btn-back"
  101. @click="shortType = !shortType"
  102. ></v-btn>
  103. </div>
  104. </section>
  105. <v-dialog v-model="logoutPop" persistent width="350">
  106. <div class="v-common-dialog-wrapper custom-dialog">
  107. <strong class="modal-tit"> </strong>
  108. <div class="v-common-dialog-content">
  109. <p class="modal-txt">시스템에서 로그아웃 하시겠습니까?</p>
  110. </div>
  111. <div class="btn-wrap">
  112. <v-btn class="custom-btn btn-white" @click="logoutPop = false"> 취소 </v-btn>
  113. <v-btn @click="fnLogout()" class="custom-btn btn-purple"> 확인 </v-btn>
  114. </div>
  115. </div>
  116. </v-dialog>
  117. </template>
  118. <script setup>
  119. /************************
  120. * import
  121. ************************/
  122. import { useRoute } from "vue-router";
  123. import useAxios from "~/composables/useAxios";
  124. import useErrorHandler from "~/composables/useErrorHandler";
  125. /************************
  126. * plugins inject
  127. ************************/
  128. const { $dayjs, $log, $eventBus, $toast } = useNuxtApp();
  129. const route = useRoute();
  130. /************************
  131. * data & created
  132. ************************/
  133. let pageId = "leftMenu";
  134. let logoutPop = ref(false);
  135. let arrMenuLists = ref([]);
  136. let currentTopMenuLocation = ref("");
  137. let currentMenuLocation = ref("");
  138. let shortType = ref(false);
  139. let twoDept = ref(null);
  140. /***********
  141. * watch
  142. ***********/
  143. watch(
  144. route,
  145. (newv, oldv) => {
  146. let arrPaths = newv.path.split("/").filter((str) => str !== "");
  147. currentTopMenuLocation.value = `/${arrPaths[0]}`;
  148. currentMenuLocation.value = `/${arrPaths[0]}/${arrPaths[1]}`;
  149. },
  150. { deep: true, immediate: true }
  151. );
  152. /************************
  153. * Methods
  154. ************************/
  155. // 메뉴 목록 조회하기
  156. function fnGetMenu() {
  157. console.log("%c [print][]", "color:#10cdbc", "좌측메뉴 조회하기");
  158. useAxios()
  159. .post("/menu/selectMenuList")
  160. .then((res) => {
  161. $log.debug("[leftMenu][fnGetMenu][success]");
  162. let arrRes = res.data.data;
  163. arrRes.forEach((item, index) => {
  164. if (item.p_menu_seq == 0) {
  165. item.sub = [];
  166. arrMenuLists.value.push(item);
  167. }
  168. });
  169. arrMenuLists.value.forEach((item, index) => {
  170. arrRes.forEach((itemSub, indexSub) => {
  171. if (item.menu_seq == itemSub.p_menu_seq) {
  172. if (arrMenuLists.value[index].menu_url == "") {
  173. arrMenuLists.value[index].menu_url = itemSub.menu_url;
  174. }
  175. arrMenuLists.value[index].sub.push(itemSub);
  176. }
  177. });
  178. });
  179. })
  180. .catch((error) => {
  181. $log.debug("[leftMenu][fnGetMenu][error]");
  182. useErrorHandler().fnSetCommErrorHandle(error, fnGetMenu);
  183. })
  184. .finally(() => {
  185. $log.debug("[leftMenu][fnGetMenu][finished]");
  186. });
  187. }
  188. // 메뉴 이벤트 처리
  189. function fnMenuEvent(obj) {
  190. if (obj.p_menu_seq == 0) {
  191. // top menu
  192. $(".depth1 > li").removeClass("active");
  193. $(".depth2").hide();
  194. let elTopMenu = $("#menu_" + obj.menu_seq);
  195. if (elTopMenu.hasClass("active")) {
  196. elTopMenu.removeClass("active");
  197. elTopMenu.find(".depth2").hide();
  198. } else {
  199. elTopMenu.addClass("active");
  200. if (obj.sub && obj.sub.length > 0) {
  201. elTopMenu.find(".depth2").show();
  202. }
  203. }
  204. } else {
  205. // sub menu
  206. useUtil.setPageMove(obj.menu_url);
  207. }
  208. }
  209. function focusIn(idx) {
  210. /*for(let i = 0; i < document.getElementsByClassName("depth2").length; i++){
  211. document.getElementsByClassName("depth2")[i].style.display = "none"
  212. }*/
  213. // if(document.getElementsByClassName("depth2")[idx].style.display == 'block'){
  214. // document.getElementsByClassName("depth2")[idx].style.display = "none"
  215. // }else{
  216. // for(let i = 0; i < document.getElementsByClassName("depth2").length; i++){
  217. // document.getElementsByClassName("depth2")[i].style.display = "none"
  218. // }
  219. // document.getElementsByClassName("depth2")[idx].style.display = "block"
  220. // }
  221. twoDept.value = idx;
  222. }
  223. // 메인 화면으로 이동
  224. function fnMoveHome() {
  225. useUtil.setPageMove(useAuthStore().getRedirectPage);
  226. }
  227. // 로그아웃
  228. function fnLogout() {
  229. const { logout } = useLogout()
  230. logout()
  231. }
  232. </script>
  233. <style lang="scss" scoped></style>