Menu菜单

在一个临时的面板上显示一组操作。

规则

  • 至少包含 2 个以上的菜单项。
  • 不应该被当做主要导航方式。

代码演示

菜单

  1. import { Component, ViewEncapsulation } from '@angular/core';
  2. @Component({
  3. selector: 'demo-menu-basic',
  4. template: `
  5. <div [ngClass]="[show ? 'menu-active' : '']">
  6. <div>
  7. <Navbar [leftContent]="'Menu'" [icon]="icon" (onLeftClick)="handleClick($event)" class="top-nav-bar">
  8. Here is title
  9. </Navbar>
  10. </div>
  11. <Menu
  12. *ngIf="show && initData"
  13. class="foo-menu"
  14. [data]="initData"
  15. [value]="['1', '3']"
  16. (onChange)="onChange($event)"
  17. [height]="menuHeight"
  18. >
  19. </Menu>
  20. <div
  21. *ngIf="show && !initData"
  22. style="width: 100%; height: 200px; display: flex; justify-content: center; align-items: center"
  23. >
  24. <ActivityIndicator [size]="'large'"></ActivityIndicator>
  25. </div>
  26. <div *ngIf="show" class="menu-mask1" (click)="onMaskClick()"></div>
  27. </div>
  28. <ng-template #icon>
  29. <img
  30. src="https://gw.alipayobjects.com/zos/rmsportal/iXVHARNNlmdCGnwWxQPH.svg"
  31. class="am-icon am-icon-md"
  32. alt=""
  33. />
  34. </ng-template>
  35. `,
  36. styles: [
  37. `
  38. .foo-menu {
  39. position: relative;
  40. z-index: 1000 !important;
  41. }
  42. .menu-active .top-nav-bar {
  43. z-index: 80;
  44. }
  45. .top-nav-bar {
  46. position: relative;
  47. background-color: #008ae6;
  48. color: #fff;
  49. }
  50. .menu-mask1 {
  51. content: ' ';
  52. position: absolute;
  53. top: 0;
  54. width: 100%;
  55. height: 100%;
  56. background-color: #000;
  57. opacity: 0.4;
  58. z-index: 79;
  59. }
  60. `
  61. ],
  62. encapsulation: ViewEncapsulation.None
  63. })
  64. export class DemoMenuBasicComponent {
  65. initData: Array<any>;
  66. show: boolean = false;
  67. menuHeight: number = document.documentElement.clientHeight * 0.6;
  68. dataMenu: Array<any> = [
  69. {
  70. value: '1',
  71. label: 'Food',
  72. children: [
  73. {
  74. label: 'All Foods',
  75. value: '1',
  76. disabled: false
  77. },
  78. {
  79. label: 'Chinese Food',
  80. value: '2'
  81. },
  82. {
  83. label: 'Hot Pot',
  84. value: '3'
  85. },
  86. {
  87. label: 'Buffet',
  88. value: '4'
  89. },
  90. {
  91. label: 'Fast Food',
  92. value: '5'
  93. },
  94. {
  95. label: 'Snack',
  96. value: '6'
  97. },
  98. {
  99. label: 'Bread',
  100. value: '7'
  101. },
  102. {
  103. label: 'Fruit',
  104. value: '8'
  105. },
  106. {
  107. label: 'Noodle',
  108. value: '9'
  109. },
  110. {
  111. label: 'Leisure Food',
  112. value: '10'
  113. }
  114. ]
  115. },
  116. {
  117. value: '2',
  118. label: 'Supermarket',
  119. children: [
  120. {
  121. label: 'All Supermarkets',
  122. value: '1'
  123. },
  124. {
  125. label: 'Supermarket',
  126. value: '2',
  127. disabled: true
  128. },
  129. {
  130. label: 'C-Store',
  131. value: '3'
  132. },
  133. {
  134. label: 'Personal Care',
  135. value: '4'
  136. }
  137. ]
  138. },
  139. {
  140. value: '3',
  141. label: 'Extra',
  142. isLeaf: true,
  143. children: [
  144. {
  145. label: 'you can not see',
  146. value: '1'
  147. }
  148. ]
  149. }
  150. ];
  151. onChange(value) {
  152. let label = '';
  153. this.dataMenu.forEach(dataItem => {
  154. if (dataItem.value === value[0]) {
  155. label = dataItem.label;
  156. if (dataItem.children && value[1]) {
  157. for (let i = 0; i < dataItem.children.length; i++) {
  158. const cItem = dataItem.children[i];
  159. if (cItem.value === value[1]) {
  160. label += cItem.label;
  161. }
  162. }
  163. }
  164. }
  165. });
  166. console.log(label);
  167. }
  168. handleClick(e) {
  169. e.preventDefault();
  170. this.show = !this.show;
  171. if (!this.initData) {
  172. setTimeout(() => {
  173. this.initData = this.dataMenu;
  174. }, 500);
  175. }
  176. }
  177. onMaskClick() {
  178. this.show = false;
  179. }
  180. }

单级菜单

  1. import { Component, ViewEncapsulation } from '@angular/core';
  2. @Component({
  3. selector: 'demo-menu-singleSelect',
  4. template: `
  5. <div [ngClass]="[show ? 'single-menu-active' : '']">
  6. <div>
  7. <Navbar class="single-top-nav-bar" [leftContent]="'Menu'" (onLeftClick)="handleClick($event)">
  8. Here is title
  9. </Navbar>
  10. </div>
  11. <Menu
  12. *ngIf="show && initData"
  13. class="single-foo-menu"
  14. [data]="initData"
  15. [value]="['1']"
  16. [level]="1"
  17. (onChange)="onChange($event)"
  18. [height]="menuHeight"
  19. >
  20. </Menu>
  21. <div
  22. *ngIf="show && !initData"
  23. style="width: 100% ;height: 200px; display: flex; justify-content: center; align-items: center"
  24. >
  25. <ActivityIndicator [size]="'large'"></ActivityIndicator>
  26. </div>
  27. <div *ngIf="show" class="menu-mask2" (click)="onMaskClick()"></div>
  28. </div>
  29. `,
  30. styles: [
  31. `
  32. .single-foo-menu {
  33. position: absolute;
  34. z-index: 90 !important;
  35. width: 100%;
  36. }
  37. .single-menu-active .single-top-nav-bar {
  38. z-index: 90;
  39. }
  40. .single-top-nav-bar {
  41. position: relative;
  42. background-color: #008ae6;
  43. color: #fff;
  44. }
  45. .menu-mask2 {
  46. position: absolute;
  47. top: 0;
  48. width: 100%;
  49. height: 100%;
  50. background-color: #000;
  51. opacity: 0.4;
  52. z-index: 89;
  53. }
  54. `
  55. ],
  56. encapsulation: ViewEncapsulation.None
  57. })
  58. export class DemoMenuSingleSelectComponent {
  59. initData: Array<any>;
  60. show: boolean = false;
  61. menuHeight: number = document.documentElement.clientHeight * 0.6;
  62. data: Array<any> = [
  63. {
  64. value: '1',
  65. label: 'Food'
  66. },
  67. {
  68. value: '2',
  69. label: 'Supermarket'
  70. },
  71. {
  72. value: '3',
  73. label: 'Extra',
  74. isLeaf: true
  75. }
  76. ];
  77. onChange(value) {
  78. console.log(value);
  79. }
  80. handleClick(e) {
  81. e.preventDefault();
  82. this.show = !this.show;
  83. if (!this.initData) {
  84. setTimeout(() => {
  85. this.initData = this.data;
  86. }, 500);
  87. }
  88. }
  89. onMaskClick() {
  90. this.show = false;
  91. }
  92. }

菜单多选

  1. import { Component, ViewEncapsulation } from '@angular/core';
  2. @Component({
  3. selector: 'demo-menu-multiSelect',
  4. template: `
  5. <div [ngClass]="[show ? 'multi-menu-active' : '']">
  6. <div>
  7. <Navbar [leftContent]="'Menu'" (onLeftClick)="handleClick($event)" class="multi-top-nav-bar">
  8. Here is title
  9. </Navbar>
  10. </div>
  11. <Menu
  12. *ngIf="show && initData"
  13. class="multi-foo-menu"
  14. [data]="initData"
  15. [value]="['1', ['3', '4']]"
  16. [multiSelect]="true"
  17. (onChange)="onChange($event)"
  18. (onOk)="onOk($event)"
  19. (onCancel)="onCancel()"
  20. [height]="menuHeight"
  21. >
  22. </Menu>
  23. <div
  24. *ngIf="show && !initData"
  25. style="width: 100% ;height: 200px; display: flex; justify-content: center; align-items: center"
  26. >
  27. <ActivityIndicator [size]="'large'"></ActivityIndicator>
  28. </div>
  29. <div *ngIf="show" class="menu-mask3" (click)="onMaskClick()"></div>
  30. </div>
  31. `,
  32. styles: [
  33. `
  34. .multi-foo-menu {
  35. position: absolute;
  36. z-index: 80 !important;
  37. width: 100%;
  38. }
  39. .multi-menu-active .multi-top-nav-bar {
  40. z-index: 80;
  41. }
  42. .multi-top-nav-bar {
  43. position: relative;
  44. background-color: #008ae6;
  45. color: #fff;
  46. }
  47. .menu-mask3 {
  48. content: ' ';
  49. position: absolute;
  50. top: 0;
  51. width: 100%;
  52. height: 100%;
  53. background-color: #000;
  54. opacity: 0.4;
  55. z-index: 79;
  56. }
  57. `
  58. ],
  59. encapsulation: ViewEncapsulation.None
  60. })
  61. export class DemoMenuMultiSelectComponent {
  62. initData: Array<any>;
  63. show: boolean = false;
  64. menuHeight: number = document.documentElement.clientHeight * 0.6;
  65. dataMenu: Array<any> = [
  66. {
  67. value: '1',
  68. label: 'Food',
  69. children: [
  70. {
  71. label: 'All Foods',
  72. value: '1',
  73. disabled: false
  74. },
  75. {
  76. label: 'Chinese Food',
  77. value: '2'
  78. },
  79. {
  80. label: 'Hot Pot',
  81. value: '3'
  82. },
  83. {
  84. label: 'Buffet',
  85. value: '4'
  86. },
  87. {
  88. label: 'Fast Food',
  89. value: '5'
  90. },
  91. {
  92. label: 'Snack',
  93. value: '6'
  94. },
  95. {
  96. label: 'Bread',
  97. value: '7'
  98. },
  99. {
  100. label: 'Fruit',
  101. value: '8'
  102. },
  103. {
  104. label: 'Noodle',
  105. value: '9'
  106. },
  107. {
  108. label: 'Leisure Food',
  109. value: '10'
  110. }
  111. ]
  112. },
  113. {
  114. value: '2',
  115. label: 'Supermarket',
  116. children: [
  117. {
  118. label: 'All Supermarkets',
  119. value: '1'
  120. },
  121. {
  122. label: 'Supermarket',
  123. value: '2',
  124. disabled: true
  125. },
  126. {
  127. label: 'C-Store',
  128. value: '3'
  129. },
  130. {
  131. label: 'Personal Care',
  132. value: '4'
  133. }
  134. ]
  135. },
  136. {
  137. value: '3',
  138. label: 'Extra',
  139. isLeaf: true,
  140. children: [
  141. {
  142. label: 'you can not see',
  143. value: '1'
  144. }
  145. ]
  146. }
  147. ];
  148. onChange(value) {
  149. console.log(value);
  150. }
  151. handleClick(e) {
  152. e.preventDefault();
  153. this.show = !this.show;
  154. if (!this.initData) {
  155. setTimeout(() => {
  156. this.initData = this.dataMenu;
  157. }, 500);
  158. }
  159. }
  160. onMaskClick() {
  161. this.show = false;
  162. }
  163. onOk(value) {
  164. console.log(value);
  165. this.onCancel();
  166. }
  167. onCancel() {
  168. this.show = false;
  169. }
  170. }

单级菜单多选

  1. import { Component, ViewEncapsulation } from '@angular/core';
  2. @Component({
  3. selector: 'demo-menu-singleMulti',
  4. template: `
  5. <div [ngClass]="[show ? 'single-multi-menu-active' : '']">
  6. <div>
  7. <Navbar [leftContent]="'Menu'" (onLeftClick)="handleClick($event)" class="single-multi-top-nav-bar">
  8. Here is title
  9. </Navbar>
  10. </div>
  11. <Menu
  12. *ngIf="show && initData"
  13. class="single-multi-foo-menu"
  14. [data]="initData"
  15. [value]="['1']"
  16. [level]="1"
  17. [multiSelect]="true"
  18. (onChange)="onChange($event)"
  19. (onOk)="onOk($event)"
  20. (onCancel)="onCancel()"
  21. [height]="menuHeight"
  22. >
  23. </Menu>
  24. <div
  25. *ngIf="show && !initData"
  26. style="width: 100% ;height: 200px; display: flex; justify-content: center; align-items: center"
  27. >
  28. <ActivityIndicator [size]="'large'"></ActivityIndicator>
  29. </div>
  30. <div *ngIf="show" class="menu-mask4" (click)="onMaskClick()"></div>
  31. </div>
  32. `,
  33. styles: [
  34. `
  35. .single-multi-foo-menu {
  36. position: absolute;
  37. z-index: 70 !important;
  38. width: 100%;
  39. }
  40. .single-multi-menu-active .single-multi-top-nav-bar {
  41. z-index: 80;
  42. }
  43. .single-multi-top-nav-bar {
  44. position: relative;
  45. background-color: #008ae6;
  46. color: #fff;
  47. }
  48. .menu-mask4 {
  49. content: ' ';
  50. position: absolute;
  51. top: 0;
  52. width: 100%;
  53. height: 100%;
  54. background-color: #000;
  55. opacity: 0.4;
  56. z-index: 69;
  57. }
  58. `
  59. ],
  60. encapsulation: ViewEncapsulation.None
  61. })
  62. export class DemoMenuSingleMultiComponent {
  63. initData: Array<any>;
  64. show: boolean = false;
  65. menuHeight: number = document.documentElement.clientHeight * 0.6;
  66. data: Array<any> = [
  67. {
  68. value: '1',
  69. label: 'Food'
  70. },
  71. {
  72. value: '2',
  73. label: 'Supermarket'
  74. },
  75. {
  76. value: '3',
  77. label: 'Extra',
  78. isLeaf: true
  79. }
  80. ];
  81. onChange(value) {
  82. console.log(value);
  83. }
  84. handleClick(e) {
  85. e.preventDefault();
  86. this.show = !this.show;
  87. if (!this.initData) {
  88. setTimeout(() => {
  89. this.initData = this.data;
  90. }, 500);
  91. }
  92. }
  93. onMaskClick() {
  94. this.show = false;
  95. }
  96. onOk(value) {
  97. console.log(value);
  98. this.onCancel();
  99. }
  100. onCancel() {
  101. console.log('onCancel');
  102. this.show = false;
  103. }
  104. }

Menu菜单 - 图1

API

参数说明类型默认值
[data]数据(isLeaf 设置后 children 无效)Array<{label: string, value, disabled?, children<data>?, isLeaf?}>[]
[level]菜单级数1 | 22
[value]初始值,一级和二级筛选数据的value组成的数组。在多选状态下,如果为二级菜单,则数组的第一个元素为一级菜单的选项,数组的第二个元素是一个数组,里面包含了二级菜单的多选项;如果为一级菜单,则数组所有元素都是多选项Array-
[height]筛选组件的高度numberdocument.documentElement.clientHeight / 2
[multiSelect]是否支持菜单多选booleanfalse
(onChange)选择后的回调函数EventEmitter<object>-
(onOk)多选状态下确认按钮回调EventEmitter<object>-
(onCancel)多选状态下取消按钮回调EventEmitter<void>-