<template>
  <a-layout-sider
    v-model="defaultLayout.collapsed"
    breakpoint="md"
    collapsed-width="0"
    :width="defaultLayout.sideMenuWidth"
    :theme="sideTheme"
    :class="['side-menu', isMobile ? null : 'shadow']"
    :collapsible="collapsible"
    :trigger="null"
    :style="{
      transition: 'all 0s ease 0s',
      overflow: 'hidden',
    }"
  >
    <div :class="['side-menu-header', theme]">
      <span class="header-menu-button" @click="showMenu">
        <a-icon type="unordered-list" style="font-size: 24px" />
      </span>
      <!-- LOGO -->
      <router-link to="/" class="logo">
        <div
          v-if="homeLogoUrl"
          class="header-logo-img"
          :style="{
            backgroundImage: `url(${homeLogoUrl})`,
          }"
        />
        <span v-else class="anticon header-logo">
          <svg-icon
            icon-class="logo"
            style="width: 74px; height: 26px; margin-top: 0"
          />
        </span>
      </router-link>
    </div>
    <i-menu
      class="menu"
      :options="menuData"
      :menu-theme="menuTheme"
      style="overflow-y: auto; overflow-x: hidden; height: calc(100vh - 50px)"
      :collapsed="defaultLayout.collapsed"
      @select="onSelect"
    />
    <a-drawer
      placement="left"
      wrap-class-name="header-wrap-menu"
      width="876px"
      :not-found-content="null"
      :visible="visible"
      :closable="false"
      @close="onClose"
    >
      <a-select
        class="menu-search"
        show-search
        :placeholder="$t('PLACEENTER')"
        :value="searchMenuKey"
        :default-active-first-option="false"
        :filter-option="false"
        :not-found-content="null"
        @search="handleSearchMenu"
      >
        <a-icon slot="suffixIcon" type="search" />
        <a-select-option
          v-for="item in searchMenuResult"
          :key="item.id"
          @click.native="searchResultClick"
        >
          {{ $t(item.menuName) }}
        </a-select-option>
      </a-select>
      <a-tabs :default-active-key="activatedModule" tab-position="left">
        <a-tab-pane v-for="module in menuTreeData" :key="module.id">
          <template slot="tab">
            {{ $t(module.menuName) }}
            <Icon
              type="icon-dir-f-double-right"
              style="float: right; line-height: 50px"
              :size="16"
            />
          </template>
          <div class="menu-container">
            <div
              v-for="second in module.children || []"
              :key="second.id"
              class="second-menu"
              style="break-inside: avoid"
            >
              <div class="second-menu__title">
                <Icon v-if="second.icon" :type="second.icon" :size="14" />
                <span class="text">{{ $t(second.menuName) }}</span>
              </div>

              <div
                v-for="third in second.children || []"
                :key="third.id"
                class="third-menu"
              >
                <div
                  class="third-menu__title"
                  @click.stop="() => goJump(third)"
                >
                  <Icon v-if="third.icon" :type="third.icon" :size="12" />
                  <span class="text">{{ $t(third.menuName) }}</span>
                  <div v-if="third.menuPath" class="collect">
                    <span
                      class="collect-no"
                      :style="{
                        display: collectedMenuIds.includes(third.id)
                          ? 'none'
                          : 'block',
                      }"
                      @click.stop="
                        () => defaultLayout.toggleCollect(third, true)
                      "
                    >
                      <Icon type="icon-cur-star" :size="12" />
                    </span>
                    <span
                      v-if="collectedMenuIds.includes(third.id)"
                      class="collect-yes"
                      @click.stop="
                        () => defaultLayout.toggleCollect(third, false)
                      "
                    >
                      <Icon type="icon-cur-star" :size="12" />
                    </span>
                  </div>
                </div>
                <div
                  v-if="third.children && third.children.length"
                  class="third-menu__content"
                >
                  <div
                    v-for="four in third.children"
                    :key="four.id"
                    class="four-menu"
                  >
                    <div
                      class="four-menu__title"
                      @click.stop="() => goJump(four)"
                    >
                      <span class="text">{{ $t(four.menuName) }}</span>
                      <div v-if="four.menuPath" class="collect">
                        <span
                          class="collect-no"
                          :style="{
                            display: collectedMenuIds.includes(four.id)
                              ? 'none'
                              : 'block',
                          }"
                          @click.stop="
                            () => defaultLayout.toggleCollect(four, true)
                          "
                        >
                          <Icon type="icon-cur-star" :size="12" />
                        </span>
                        <span
                          v-if="collectedMenuIds.includes(four.id)"
                          class="collect-yes"
                          @click.stop="
                            () => defaultLayout.toggleCollect(four, false)
                          "
                        >
                          <Icon type="icon-cur-star" :size="12" />
                        </span>
                      </div>
                    </div>
                  </div>
                </div>
              </div>
            </div>
          </div>
        </a-tab-pane>
      </a-tabs>
    </a-drawer>
  </a-layout-sider>
</template>

<script>
import { mapState } from "vuex";
import { debounce } from "lodash";
import { Icon } from "@mega-design/ui-vue";
import ApiConstant from "@/api/ApiConstant";
import { fetchFileUrl } from "@/utils/file";
import IMenu from "./menu";

export default {
  name: "SideMenu",
  components: { IMenu, Icon },
  inject: ["defaultLayout"],
  props: {
    collapsible: {
      type: Boolean,
      required: false,
      default: false,
    },
    menuData: {
      type: Array,
      required: true,
    },
    theme: {
      type: String,
      required: false,
      default: "dark",
    },
  },
  data() {
    return {
      visible: false,
      searchMenuKey: undefined,
      searchMenuResult: [],
    };
  },
  computed: {
    ...mapState({
      systemConfig: (state) => state.app.systemConfig,
      menus: (state) => state.account.menus,
      activatedModule: (state) => state.activatedModule,
      favoritesMenu: (state) => state.account.favoritesMenu,
      isMobile: (state) => state.setting.isMobile,
    }),
    sideTheme() {
      return ["light", "mix"].includes(this.theme) ? "light" : "dark";
    },
    menuTheme() {
      return ["light", "mix"].includes(this.theme) ? "light" : "dark";
    },
    collectedMenuIds() {
      return (this.favoritesMenu || []).map((item) => item.id);
    },
    menuTreeData() {
      // 菜单删除按钮层 处理
      const fn = (data = [], res = []) => {
        data.forEach((item, index) => {
          const { children, ...rest } = item;
          res.push({ ...rest });
          if (children?.length) {
            if (children.every((e) => e.menuType !== "BUTTON")) {
              res[index].children = [];
              fn(children, res[index].children);
            }
          }
        });
        return res;
      };
      return fn(this.menus);
    },
    homeLogoUrl() {
      if (this.systemConfig.FILE_SERVER && this.systemConfig.HOME_LOGO) {
        return fetchFileUrl(this.systemConfig.HOME_LOGO, this);
      }
      return "";
    },
  },
  methods: {
    goJump(data) {
      this.visible = false;
      this.defaultLayout.goRoute(data);
    },
    searchResultClick({ item }) {
      const { index } = item;
      this.visible = false;
      this.searchMenuKey = undefined;
      this.defaultLayout.goRoute(this.searchMenuResult[index]);
    },
    onClose() {
      this.visible = false;
    },
    showMenu() {
      this.visible = true;
    },
    onSelect(obj) {
      this.$emit("menuSelect", obj);
    },
    // 所有菜单搜索
    handleSearchMenu: debounce(function (value) {
      this.searchMenuKey = value;
      this.$axios
        .get(`${ApiConstant.PREFIX_CORE}/api/sys/menu/list-of-query`, {
          params: {
            size: 20,
            searchKey: this.searchMenuKey,
          },
        })
        .then((res) => {
          this.searchMenuResult = res.data.data;
        });
    }, 500),
  },
};
</script>

<style lang="less" scoped>
@import (optional, once) "../../theme/index.less";

.shadow {
  box-shadow: 2px 0 6px rgba(0, 21, 41, 0.1);
}
.side-menu {
  min-height: 100vh;
  overflow-x: hidden;
  overflow-y: auto;
  z-index: 12;
  .side-menu-header {
    position: relative;
    height: 50px;
    padding-left: 44px;
    line-height: 50px;
    background-color: @primary-color;
    &.night {
      background-color: transparent;
    }
    .header-menu-button {
      position: absolute;
      left: 0;
      top: 0;
      color: @menu-dark-color;
      padding: 0 14px;
      font-size: 24px;
      cursor: pointer;
      &:hover {
        color: @menu-dark-highlight-color;
      }
    }
    .logo {
      display: inline-flex;
      align-items: center;
      height: 50px;
      line-height: 50px;
      padding: 0 12px 0 24px;
      font-size: 30px;
      cursor: pointer;
      .header-logo {
        width: 74px;
        display: inline-block;
        color: @menu-dark-highlight-color;
        cursor: pointer;
      }
      .header-logo-img {
        width: 136px;
        height: 36px;
        background-repeat: no-repeat;
        background-position: center;
        background-size: contain;
      }
    }
    &.light {
      background-color: @white;
      .logo .header-logo {
        color: #005583;
      }
      .header-menu-button {
        color: @text-color-second;
        :hover {
          color: @primary-color;
        }
      }
    }
  }
  /deep/ .anticon {
    font-size: 16px;
  }
}
</style>
