• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1/*
2 * Copyright (C) 2022 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 *     http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16import { BaseElement, element } from '../BaseElement';
17import './LitMainMenuItem';
18import './LitMainMenuGroup';
19import { LitMainMenuGroup } from './LitMainMenuGroup';
20import { LitMainMenuItem } from './LitMainMenuItem';
21
22const initHtmlStyle:string = `
23    <style>
24        :host{
25            width: 248px;
26            height: 100vh;
27            display: flex;
28            flex-direction: column;
29            background-color: #fff;
30        }
31        .menu-body ::-webkit-scrollbar-thumb
32        {
33            background-color: var(--dark-background,#FFFFFF);
34            border-radius:10px;
35
36        }
37        .menu-body ::-webkit-scrollbar-track
38        {
39            border-radius:10px;
40            background-color:#F5F5F5;
41
42        }
43        .header{
44            display: grid;
45            width: 100%;
46            height: 56px;
47            font-size: 1.4rem;
48            padding-left: 20px;
49            gap: 0 20px;
50            box-sizing: border-box;
51            grid-template-columns: min-content 1fr min-content;
52            grid-template-rows: auto;
53            color: #47A7E0;
54            background-color: var(--dark-background1);
55            border-bottom: 1px solid var(--dark-background1,#EFEFEF);
56        }
57        .bottom{
58            width: 100%;
59            display: flex;
60            justify-content: space-between;
61        }
62        .header *{
63            user-select: none;
64            align-self: center;
65        }
66        .version{
67            width: 15rem;
68            padding: 20px 0;
69            text-align: center;
70            color: #94979d;
71            font-size: 0.6rem;
72        }
73        .color, .customColor{
74            cursor: pointer;
75            font-size: 0.6rem;
76            padding: 20px 0px 20px 20px;
77        }
78        *{
79            box-sizing: border-box;
80        }
81        .menu-button{
82            display: flex;
83            align-content: center;
84            justify-content: right;
85            cursor: pointer;
86            height: 47px;
87            width: 48px;
88        }
89        </style>
90    `;
91
92@element('lit-main-menu')
93export class LitMainMenu extends BaseElement {
94  private slotElements: Element[] | undefined;
95  private _menus: Array<MenuGroup> | undefined;
96
97  static get observedAttributes() {
98    return [];
99  }
100
101  get menus(): Array<MenuGroup> | undefined {
102    return this._menus;
103  }
104
105  set menus(value: Array<MenuGroup> | undefined) {
106    this._menus = value;
107    this.shadowRoot?.querySelectorAll('lit-main-menu-group').forEach((a) => a.remove());
108    let menuBody = this.shadowRoot?.querySelector('.menu-body');
109    if (this.getAttribute('main_menu') === '1' && window.localStorage.getItem('Theme') == 'dark') {
110      this.style.backgroundColor = '#262f3c';
111    } else {
112      this.style.backgroundColor = '#fff';
113    }
114    value?.forEach((it) => {
115      let group: LitMainMenuGroup = new LitMainMenuGroup();
116      group.setAttribute('title', it.title || '');
117      if (it.describe !== '') {
118        group.setAttribute('describe', it.describe || '');
119      } else {
120        group.removeAttribute('describe');
121      }
122      group.setAttribute('icon', it.icon || '');
123      if (it.collapsed) {
124        group.setAttribute('collapsed', '');
125      } else {
126        group.removeAttribute('collapsed');
127      }
128      let groupName: LitMainMenuGroup = group!.shadowRoot!.querySelector('.group-name') as LitMainMenuGroup;
129      let groupDescribe: LitMainMenuGroup = group!.shadowRoot!.querySelector('.group-describe') as LitMainMenuGroup;
130      menuBody?.appendChild(group);
131      it.children?.forEach((item: any) => {
132        if (item.children && item.children.length > 0) {
133          let secondGroup: LitMainMenuGroup = new LitMainMenuGroup();
134          secondGroup.setAttribute('title', item.title || '');
135          if (item.describe !== '') {
136            secondGroup.setAttribute('describe', item.describe || '');
137          } else {
138            secondGroup.removeAttribute('describe');
139          }
140          this.setChildren(item,group,groupName,groupDescribe,secondGroup);
141        } else {
142          this.notChildren(item,group,groupName,groupDescribe);
143        }
144      });
145    });
146  }
147
148  setChildren(item:any,group: LitMainMenuGroup,groupName: LitMainMenuGroup,groupDescribe: LitMainMenuGroup,secondGroup: LitMainMenuGroup):void{
149    secondGroup.setAttribute('icon', item.icon || '');
150    if (item.second) {
151      secondGroup.setAttribute('second', '');
152    } else {
153      secondGroup.removeAttribute('second');
154    }
155    if (item.collapsed) {
156      secondGroup.setAttribute('collapsed', '');
157    } else {
158      secondGroup.removeAttribute('collapsed');
159    }
160    group?.appendChild(secondGroup);
161    item.children?.forEach((v: any) => {
162      let th = new LitMainMenuItem();
163      th.setAttribute('icon', v.icon || '');
164      th.setAttribute('title', v.title || '');
165      if (this.getAttribute('main_menu') === '1' && window.localStorage.getItem('Theme') === 'dark') {
166        groupName.style.color = 'white';
167        groupDescribe.style.color = 'white';
168        th!.style.color = 'white';
169      } else {
170        groupName.style.color = 'black';
171        groupDescribe.style.color = 'black';
172        th!.style.color = 'black';
173      }
174      if (v.fileChoose) {
175        th.setAttribute('file', '');
176        th.addEventListener('file-change', (e) => {
177          if (v.fileHandler && !th.disabled) {
178            v.fileHandler(e);
179          }
180        });
181      } else {
182        th.removeAttribute('file');
183        th.addEventListener('click', (e) => {
184          if (v.clickHandler && !th.disabled) {
185            v.clickHandler(v);
186          }
187        });
188      }
189      if (v.disabled != undefined) {
190        th.disabled = v.disabled;
191      }
192      secondGroup.appendChild(th);
193    });
194  }
195
196  notChildren(item:any,group: LitMainMenuGroup,groupName: LitMainMenuGroup,groupDescribe: LitMainMenuGroup):void{
197    let th = new LitMainMenuItem();
198    th.setAttribute('icon', item.icon || '');
199    th.setAttribute('title', item.title || '');
200    if (this.getAttribute('main_menu') === '1' && window.localStorage.getItem('Theme') === 'dark') {
201      groupName.style.color = 'white';
202      groupDescribe.style.color = 'white';
203      th!.style.color = 'white';
204    } else {
205      groupName.style.color = 'black';
206      groupDescribe.style.color = 'black';
207      th!.style.color = 'black';
208    }
209    if (item.fileChoose) {
210      th.setAttribute('file', '');
211      th.addEventListener('file-change', (e) => {
212        if (item.fileHandler && !th.disabled) {
213          item.fileHandler(e);
214        }
215      });
216    } else {
217      th.removeAttribute('file');
218      th.addEventListener('click', (e) => {
219        if (item.clickHandler && !th.disabled) {
220          item.clickHandler(item);
221        }
222      });
223    }
224    if (item.disabled != undefined) {
225      th.disabled = item.disabled;
226    }
227    group?.appendChild(th);
228  }
229
230  initElements(): void {
231    let st: HTMLSlotElement | null | undefined = this.shadowRoot?.querySelector('#st');
232    st?.addEventListener('slotchange', (e) => {
233      this.slotElements = st?.assignedElements();
234      this.slotElements?.forEach((it) => {
235        it.querySelectorAll('lit-main-menu-item').forEach((cell) => {});
236      });
237    });
238    let versionDiv: HTMLElement | null | undefined = this.shadowRoot?.querySelector<HTMLElement>('.version');
239    versionDiv!.innerText = (window as any).version || '';
240  }
241
242  initHtml(): string {
243    return `
244        ${initHtmlStyle}
245        <div class="header" name="header">
246            <img src="img/logo.png"/>
247                <div class="menu-button">
248                    <lit-icon name="menu" size="20" color="var(blue,#4D4D4D)"></lit-icon>
249                </div>
250            </div>
251            <div class="menu-body" style="overflow: auto;overflow-x:hidden;height: 100%">
252                <slot id="st" ></slot>
253                </div>
254        <div class="bottom">
255             <div class="customColor">
256                <lit-icon name="bg-colors" size="20" color="grey"></lit-icon>
257             </div>
258             <div class="version" style="">
259             </div>
260        </div>`;
261  }
262}
263
264export interface MenuGroup {
265  title: string;
266  describe: string;
267  second: boolean;
268  collapsed: boolean;
269  children: any;
270  icon: string;
271}
272
273export interface MenuItem {
274  icon: string;
275  title: string;
276  disabled?: boolean;
277  fileChoose?: boolean;
278  clickHandler?: Function;
279  fileHandler?: Function;
280}
281