Menu.tsx 2.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118
  1. import { css } from "@linaria/core";
  2. import { Dropdown, Menu } from "ant-design-vue";
  3. import { defineComponent } from "vue";
  4. import { RouterLink } from "vue-router";
  5. import { any } from "vue-types";
  6. export default defineComponent({
  7. props: {
  8. data: any(),
  9. },
  10. setup(props) {
  11. return () => (
  12. <div class={MenuLayout}>
  13. {props.data.map((e: CategoryItem) => {
  14. return <Menus data={e} />;
  15. })}
  16. </div>
  17. );
  18. },
  19. });
  20. const Menus = defineComponent({
  21. props: {
  22. data: any(),
  23. },
  24. setup(props) {
  25. const menuRender = (dropUrls: any) => {
  26. return (
  27. <Menu class={DropMenu}>
  28. {dropUrls.map((e: CategoryItem) => {
  29. return (
  30. <Menu.Item>
  31. <RouterLink to={`/detail/${e._id}`}>{e.name}</RouterLink>
  32. </Menu.Item>
  33. );
  34. })}
  35. </Menu>
  36. );
  37. };
  38. return () => {
  39. const menu = props.data;
  40. return (
  41. <>
  42. {menu.children && menu.children.length > 0 ? (
  43. <Dropdown overlay={menuRender(menu.children)}>
  44. <RouterLink to={`/detail/${menu._id}`}>{menu.name}</RouterLink>
  45. </Dropdown>
  46. ) : (
  47. <RouterLink to={`/detail/${menu._id}`}>{menu.name}</RouterLink>
  48. )}
  49. </>
  50. );
  51. };
  52. },
  53. });
  54. const MenuLayout = css`
  55. display: flex;
  56. align-items: center;
  57. a {
  58. flex: 1;
  59. position: relative;
  60. margin-top: 16px;
  61. padding-bottom: 22px;
  62. font-size: 16px;
  63. text-align: center;
  64. color: rgba(255, 255, 255, 0.8);
  65. &:hover {
  66. color: rgba(255, 255, 255, 1);
  67. &::before {
  68. width: 24px;
  69. }
  70. }
  71. &::before {
  72. content: "";
  73. position: absolute;
  74. bottom: 10px;
  75. left: 50%;
  76. transform: translateX(-50%);
  77. width: 0;
  78. height: 2px;
  79. background-color: rgba(255, 255, 255, 1);
  80. transition: width 0.3s ease-in-out;
  81. }
  82. &::after {
  83. content: "";
  84. position: absolute;
  85. top: 0;
  86. right: 0;
  87. height: 16px;
  88. border-right: 1px solid rgba(255, 255, 255, 0.3);
  89. transform: skewX(-15deg);
  90. }
  91. &:last-child {
  92. &::after {
  93. display: none;
  94. }
  95. }
  96. }
  97. `;
  98. const DropMenu = css`
  99. &.ant-dropdown-menu {
  100. padding: 10px 0;
  101. border-radius: 0;
  102. .ant-dropdown-menu-item {
  103. padding: 0;
  104. &:hover {
  105. a {
  106. color: var(--vt-c-primary);
  107. }
  108. }
  109. a {
  110. padding: 8px 12px;
  111. display: block;
  112. text-align: center;
  113. }
  114. }
  115. }
  116. `;