{"version":3,"file":"JSidebarAdvanced.vue2.cjs","sources":["../../../../src/components/organisms/JSidebarAdvanced.vue"],"sourcesContent":["<script setup lang=\"ts\">\r\nimport { ref, computed, watch } from 'vue'\r\nimport { useRoute } from 'vue-router'\r\nimport type { SidebarMenuItem, MenuPermission, MenuClickEvent } from '@/types/sidebar-menu.types'\r\nimport JDynamicMenuItem from './JSidebarSimple/JDynamicMenuItem.vue'\r\nimport JInput from '@/components/atoms/JInput.vue'\r\nimport JIcon from '@/components/atoms/JIcon.vue'\r\nimport { cn } from '@/lib/utils'\r\n\r\n/**\r\n * JSidebarAdvanced - 고급 사이드바 컴포넌트\r\n * Advanced Sidebar Component\r\n * \r\n * @description\r\n * 검색, 즐겨찾기, 다단계 메뉴를 지원하는 고급 사이드바 컴포넌트입니다.\r\n * 기본 메뉴와 즐겨찾기 탭을 제공합니다.\r\n * \r\n * @example\r\n * ```vue\r\n * <JSidebarAdvanced\r\n *   :menu-items=\"menuItems\"\r\n *   :permissions=\"userPermissions\"\r\n *   :favorites=\"favoriteMenuKeys\"\r\n *   @menu-click=\"handleMenuClick\"\r\n *   @favorite-change=\"handleFavoriteChange\"\r\n * />\r\n * ```\r\n * \r\n * @example JSON 메뉴 데이터 예시\r\n * ```json\r\n * [\r\n *   {\r\n *     \"label\": \"대시보드\",\r\n *     \"icon\": \"house\",\r\n *     \"menuType\": \"L\",\r\n *     \"menuKey\": 1,\r\n *     \"path\": \"/dashboard\"\r\n *   },\r\n *   {\r\n *     \"label\": \"재고 관리\",\r\n *     \"icon\": \"package\",\r\n *     \"menuType\": \"F\",\r\n *     \"menuKey\": 2,\r\n *     \"children\": [\r\n *       {\r\n *         \"label\": \"재고 현황\",\r\n *         \"menuType\": \"L\",\r\n *         \"menuKey\": 21,\r\n *         \"path\": \"/inventory/status\"\r\n *       },\r\n *       {\r\n *         \"label\": \"입고 관리\",\r\n *         \"menuType\": \"F\",\r\n *         \"menuKey\": 22,\r\n *         \"children\": [\r\n *           {\r\n *             \"label\": \"입고 등록\",\r\n *             \"menuType\": \"L\",\r\n *             \"menuKey\": 221,\r\n *             \"path\": \"/inventory/receiving/register\"\r\n *           }\r\n *         ]\r\n *       }\r\n *     ]\r\n *   }\r\n * ]\r\n * ```\r\n */\r\n\r\ntype TabType = 'menu' | 'favorites'\r\n\r\ntype StyleType = 'default' | 'minimal'\r\n\r\nconst props = withDefaults(\r\n  defineProps<{\r\n    /** 메뉴 아이템 목록 */\r\n    menuItems: SidebarMenuItem[]\r\n    /** 권한 목록 */\r\n    permissions?: MenuPermission[]\r\n    /** 즐겨찾기 메뉴 키 목록 */\r\n    favorites?: (number | string)[]\r\n    /** 스타일 타입 */\r\n    styletype?: StyleType\r\n    /** 추가 CSS 클래스 */\r\n    class?: string\r\n    /** 너비 */\r\n    width?: string\r\n    /** 표시 여부 */\r\n    isVisible?: boolean\r\n  }>(),\r\n  {\r\n    permissions: () => [],\r\n    favorites: () => [],\r\n    styletype: 'minimal',\r\n    width: '280px',\r\n    isVisible: true,\r\n  },\r\n)\r\n\r\nconst emit = defineEmits<{\r\n  /** 메뉴 클릭 이벤트 */\r\n  menuClick: [event: MenuClickEvent]\r\n  /** 즐겨찾기 변경 이벤트 */\r\n  favoriteChange: [menuKey: number | string | undefined, isFavorite: boolean]\r\n}>()\r\n\r\n// vue-router가 설정되지 않은 경우를 대비 (Storybook에서 router가 제공됨)\r\nconst route = useRoute()\r\n\r\n/**\r\n * 현재 활성 탭\r\n */\r\nconst activeTab = ref<TabType>('menu')\r\n\r\n/**\r\n * 검색어\r\n */\r\nconst searchQuery = ref('')\r\n\r\n/**\r\n * 현재 활성화된 경로\r\n */\r\nconst activePath = computed(() => route.path)\r\n\r\n/**\r\n * 확장된 메뉴 키 목록\r\n */\r\nconst expandedKeys = ref<Set<number | string>>(new Set())\r\n\r\n/**\r\n * 즐겨찾기 메뉴 아이템 목록\r\n * 즐겨찾기는 dept 없이 1단계로만 평탄화하여 표시\r\n */\r\nconst favoriteMenuItems = computed(() => {\r\n  if (!Array.isArray(props.favorites) || props.favorites.length === 0) {\r\n    return []\r\n  }\r\n\r\n  if (!Array.isArray(props.menuItems) || props.menuItems.length === 0) {\r\n    return []\r\n  }\r\n\r\n  /**\r\n   * 메뉴 아이템을 재귀적으로 순회하며 즐겨찾기만 추출\r\n   * 즐겨찾기에서는 dept 없이 1단계로만 평탄화\r\n   * menuType L(Link)만 포함하고 F(Folder)는 제외\r\n   */\r\n  const flattenFavorites = (items: SidebarMenuItem[]): SidebarMenuItem[] => {\r\n    const result: SidebarMenuItem[] = []\r\n\r\n    if (!Array.isArray(items)) {\r\n      return result\r\n    }\r\n\r\n    for (const item of items) {\r\n      const key = item.menuKey || item.label\r\n      const isFavorite = Array.isArray(props.favorites) && props.favorites.includes(key)\r\n\r\n      // 즐겨찾기이고 menuType이 L(Link)인 경우만 추가 (F는 제외)\r\n      if (isFavorite && item.menuType === 'L') {\r\n        result.push({\r\n          ...item,\r\n          children: undefined, // children 제거하여 1단계로만 표시\r\n        })\r\n      }\r\n\r\n      // 하위 메뉴도 재귀적으로 탐색\r\n      if (item.children && Array.isArray(item.children) && item.children.length > 0) {\r\n        const childFavorites = flattenFavorites(item.children)\r\n        result.push(...childFavorites)\r\n      }\r\n    }\r\n\r\n    return result\r\n  }\r\n\r\n  return flattenFavorites(props.menuItems)\r\n})\r\n\r\n/**\r\n * 검색어로 필터링된 메뉴 아이템\r\n * 재귀적으로 children까지 검색\r\n */\r\nconst filteredMenuItems = computed(() => {\r\n  if (!Array.isArray(props.menuItems) || props.menuItems.length === 0) {\r\n    return []\r\n  }\r\n\r\n  if (!searchQuery.value || searchQuery.value.trim() === '') {\r\n    return props.menuItems\r\n  }\r\n\r\n  const query = searchQuery.value.toLowerCase().trim()\r\n\r\n  /**\r\n   * 메뉴 아이템을 재귀적으로 검색\r\n   */\r\n  const searchInMenu = (items: SidebarMenuItem[]): SidebarMenuItem[] => {\r\n    const result: SidebarMenuItem[] = []\r\n\r\n    if (!Array.isArray(items)) {\r\n      return result\r\n    }\r\n\r\n    for (const item of items) {\r\n      const matchesLabel = item.label?.toLowerCase().includes(query) ?? false\r\n\r\n      // 하위 메뉴 검색\r\n      let filteredChildren: SidebarMenuItem[] | undefined = undefined\r\n      if (item.children && Array.isArray(item.children) && item.children.length > 0) {\r\n        filteredChildren = searchInMenu(item.children)\r\n      }\r\n\r\n      // 현재 메뉴나 하위 메뉴 중 하나라도 매칭되면 포함\r\n      if (matchesLabel || (Array.isArray(filteredChildren) && filteredChildren.length > 0)) {\r\n        result.push({\r\n          ...item,\r\n          children: filteredChildren,\r\n        })\r\n      }\r\n    }\r\n\r\n    return result\r\n  }\r\n\r\n  return searchInMenu(props.menuItems)\r\n})\r\n\r\n/**\r\n * 검색 결과에 따라 부모 메뉴 자동 확장\r\n * computed 외부에서 watch를 통해 처리\r\n */\r\nwatch(\r\n  () => filteredMenuItems.value,\r\n  (filtered) => {\r\n    if (!searchQuery.value || searchQuery.value.trim() === '') {\r\n      return\r\n    }\r\n\r\n    // 검색 결과에서 매칭된 하위 메뉴가 있는 부모를 찾아 확장\r\n    const findParentsWithMatches = (items: SidebarMenuItem[]): Set<number | string> => {\r\n      const keysToExpand = new Set<number | string>()\r\n\r\n      const traverse = (menuItems: SidebarMenuItem[]): void => {\r\n        if (!Array.isArray(menuItems)) {\r\n          return\r\n        }\r\n\r\n        for (const item of menuItems) {\r\n          if (item.children && Array.isArray(item.children) && item.children.length > 0) {\r\n            const key = item.menuKey || item.label\r\n            keysToExpand.add(key)\r\n            traverse(item.children)\r\n          }\r\n        }\r\n      }\r\n\r\n      traverse(items)\r\n      return keysToExpand\r\n    }\r\n\r\n    const keysToExpand = findParentsWithMatches(filtered)\r\n    keysToExpand.forEach(key => {\r\n      expandedKeys.value.add(key)\r\n    })\r\n  },\r\n  { immediate: false }\r\n)\r\n\r\n/**\r\n * 검색어로 필터링된 즐겨찾기 메뉴 아이템\r\n * 즐겨찾기는 이미 평탄화되어 있으므로 단순 필터링만 수행\r\n */\r\nconst filteredFavoriteItems = computed(() => {\r\n  if (!Array.isArray(favoriteMenuItems.value) || favoriteMenuItems.value.length === 0) {\r\n    return []\r\n  }\r\n\r\n  if (!searchQuery.value || searchQuery.value.trim() === '') {\r\n    return favoriteMenuItems.value\r\n  }\r\n\r\n  const query = searchQuery.value.toLowerCase().trim()\r\n\r\n  // 즐겨찾기는 이미 평탄화되어 1단계이므로 단순 필터링만 수행\r\n  return favoriteMenuItems.value.filter((item) =>\r\n    item.label?.toLowerCase().includes(query) ?? false\r\n  )\r\n})\r\n\r\n\r\n/**\r\n * 탭 변경 핸들러\r\n * 탭 전환 시 검색 쿼리를 초기화하여 각 탭의 독립적인 검색 상태 유지\r\n */\r\nconst handleTabChange = (tab: TabType) => {\r\n  if (activeTab.value !== tab) {\r\n    activeTab.value = tab\r\n    // 탭 전환 시 검색 쿼리 초기화 (선택적 - UX 고려)\r\n    // 검색 쿼리를 유지하려면 아래 라인을 제거하세요\r\n    searchQuery.value = ''\r\n  }\r\n}\r\n\r\n/**\r\n * 확장 상태 변경 핸들러\r\n */\r\nconst handleExpandChange = (menuKey: number | string | undefined, expanded: boolean) => {\r\n  if (!menuKey) return\r\n\r\n  if (expanded) {\r\n    expandedKeys.value.add(menuKey)\r\n  } else {\r\n    expandedKeys.value.delete(menuKey)\r\n  }\r\n}\r\n\r\n/**\r\n * 메뉴 클릭 핸들러\r\n */\r\nconst handleMenuClick = (event: MenuClickEvent) => {\r\n  emit('menuClick', event)\r\n}\r\n\r\n/**\r\n * 즐겨찾기 토글 핸들러\r\n */\r\nconst handleFavoriteToggle = (menuKey: number | string | undefined) => {\r\n  if (!menuKey) return\r\n\r\n  const isFavorite = props.favorites?.includes(menuKey) ?? false\r\n  emit('favoriteChange', menuKey, !isFavorite)\r\n}\r\n\r\n/**\r\n * 메뉴 아이템에서 특정 menuKey를 찾는 헬퍼 함수\r\n */\r\nconst findMenuItemByKey = (items: SidebarMenuItem[], targetKey: number | string): SidebarMenuItem | null => {\r\n  for (const item of items) {\r\n    const key = item.menuKey || item.label\r\n    if (key === targetKey) {\r\n      return item\r\n    }\r\n    if (item.children && item.children.length > 0) {\r\n      const found = findMenuItemByKey(item.children, targetKey)\r\n      if (found) return found\r\n    }\r\n  }\r\n  return null\r\n}\r\n\r\n/**\r\n * 메뉴가 즐겨찾기인지 확인 (L 타입만 즐겨찾기 가능)\r\n */\r\nconst isFavorite = (menuKey: number | string | undefined): boolean => {\r\n  if (!menuKey) return false\r\n  if (!props.favorites?.includes(menuKey)) return false\r\n  \r\n  // menuType이 L인 경우만 즐겨찾기로 인정\r\n  const menuItem = findMenuItemByKey(props.menuItems, menuKey)\r\n  return menuItem?.menuType === 'L'\r\n}\r\n\r\n/**\n * 스타일 프리셋\n */\nconst STYLE_PRESETS: Record<StyleType, {\n  containerClass: string\n  tabContainerClass: string\n  tabButtonClass: string\n  searchContainerClass: string\n  menuContainerClass: string\n}> = {\n  default: {\n    containerClass: 'h-full bg-background border-r border-border flex flex-col',\n    tabContainerClass: 'flex border-b border-border',\n    tabButtonClass: 'flex-1 px-3 py-1.5 text-xs font-medium transition-colors border-b-2 hover:bg-accent/50',\n    searchContainerClass: 'p-1.5 border-b border-border',\n    menuContainerClass: 'flex-1 overflow-y-auto p-1.5 space-y-0.5',\n  },\n  minimal: {\n    containerClass: 'h-full bg-background border-r border-border flex flex-col',\n    tabContainerClass: 'flex border-b border-border',\n    tabButtonClass: 'flex-1 px-2 py-1 text-xs font-medium transition-colors border-b-2',\n    searchContainerClass: 'p-1 border-b border-border',\n    menuContainerClass: 'flex-1 overflow-y-auto p-1 space-y-0.5',\n  },\n}\n\r\nconst preset = computed(() => {\r\n  return STYLE_PRESETS[props.styletype] ?? STYLE_PRESETS.default\r\n})\r\n\r\n/**\r\n * 루트 클래스\r\n */\r\nconst rootClasses = computed(() => {\r\n  return cn(\r\n    preset.value.containerClass,\r\n    props.class\r\n  )\r\n})\r\n</script>\r\n\r\n<template>\r\n  <Transition name=\"slide\">\r\n    <aside v-show=\"props.isVisible\" :class=\"rootClasses\" :style=\"{ width }\">\r\n    <!-- 탭 헤더 -->\r\n    <div :class=\"preset.tabContainerClass\">\r\n      <button\r\n        :class=\"cn(\r\n          preset.tabButtonClass,\r\n          activeTab === 'menu'\r\n            ? 'border-primary text-primary'\r\n            : 'border-transparent text-muted-foreground hover:text-foreground'\r\n        )\"\r\n        @click=\"handleTabChange('menu')\"\r\n      >\r\n        기본메뉴\r\n      </button>\r\n      <button\r\n        :class=\"cn(\r\n          preset.tabButtonClass,\r\n          activeTab === 'favorites'\r\n            ? 'border-primary text-primary'\r\n            : 'border-transparent text-muted-foreground hover:text-foreground'\r\n        )\"\r\n        @click=\"handleTabChange('favorites')\"\r\n      >\r\n        즐겨찾기\r\n      </button>\r\n    </div>\r\n\r\n    <!-- 검색 영역 -->\r\n    <div :class=\"preset.searchContainerClass\">\r\n      <div class=\"relative\">\r\n        <JIcon\r\n          name=\"search\"\r\n          size=\"sm\"\r\n          class=\"absolute left-2 top-1/2 -translate-y-1/2 text-muted-foreground\"\r\n        />\r\n        <JInput\r\n          v-model=\"searchQuery\"\r\n          placeholder=\"메뉴 검색...\"\r\n          :class=\"cn(\r\n            'pl-8',\r\n            props.styletype === 'minimal' && 'h-8 text-xs'\r\n          )\"\r\n        />\r\n      </div>\r\n    </div>\r\n\r\n    <!-- 메뉴 목록 -->\r\n    <div :class=\"preset.menuContainerClass\">\r\n      <template v-if=\"activeTab === 'menu'\">\r\n        <template v-if=\"filteredMenuItems.length > 0\">\r\n          <div\r\n            v-for=\"(item, index) in filteredMenuItems\"\r\n            :key=\"item.menuKey || item.label || index\"\r\n            class=\"flex items-center group\"\r\n          >\r\n            <JDynamicMenuItem\r\n              :item=\"item\"\r\n              :level=\"0\"\r\n              :permissions=\"permissions\"\r\n              :active-path=\"activePath\"\r\n              :expanded-keys=\"expandedKeys\"\r\n              :favorites=\"favorites\"\r\n              :on-favorite-toggle=\"handleFavoriteToggle\"\r\n              :is-favorite=\"isFavorite\"\r\n              :styletype=\"styletype\"\r\n              class=\"flex-1\"\r\n              @menu-click=\"handleMenuClick\"\r\n              @expand-change=\"handleExpandChange\"\r\n            />\r\n          </div>\r\n        </template>\n        <div v-else class=\"text-center py-8 text-muted-foreground\">\n          <p class=\"text-xs\">검색 결과가 없습니다.</p>\n        </div>\n      </template>\n\n      <template v-else>\n        <template v-if=\"filteredFavoriteItems.length > 0\">\n          <JDynamicMenuItem\n            v-for=\"(item, index) in filteredFavoriteItems\"\n            :key=\"item.menuKey || item.label || index\"\n            :item=\"item\"\n            :level=\"0\"\n            :permissions=\"permissions\"\n            :active-path=\"activePath\"\n            :expanded-keys=\"expandedKeys\"\n            :styletype=\"styletype\"\n            @menu-click=\"handleMenuClick\"\n            @expand-change=\"handleExpandChange\"\n          />\n        </template>\n        <div v-else class=\"text-center py-8 text-muted-foreground\">\n          <p class=\"text-xs\">즐겨찾기가 없습니다.</p>\n        </div>\n      </template>\r\n    </div>\r\n  </aside>\r\n  </Transition>\r\n</template>\r\n\r\n<style scoped>\r\n.slide-enter-active,\r\n.slide-leave-active {\r\n  transition: transform 0.3s ease, opacity 0.3s ease;\r\n}\r\n\r\n.slide-enter-from,\r\n.slide-leave-to {\r\n  transform: translateX(-100%);\r\n  opacity: 0;\r\n}\r\n</style>\r\n"],"names":["props","__props","emit","__emit","route","useRoute","activeTab","ref","searchQuery","activePath","computed","expandedKeys","favoriteMenuItems","flattenFavorites","items","result","item","key","childFavorites","filteredMenuItems","query","searchInMenu","matchesLabel","filteredChildren","watch","filtered","keysToExpand","traverse","menuItems","filteredFavoriteItems","handleTabChange","tab","handleExpandChange","menuKey","expanded","handleMenuClick","event","handleFavoriteToggle","isFavorite","findMenuItemByKey","targetKey","found","STYLE_PRESETS","preset","rootClasses","cn","_createBlock","_Transition","_createElementVNode","_normalizeClass","_unref","_hoisted_1","_createVNode","JIcon","JInput","$event","_createElementBlock","_Fragment","_openBlock","_renderList","index","JDynamicMenuItem","_hoisted_2","_cache","_hoisted_3","_vShow"],"mappings":"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"}