1/**
2 * Copyright (c) 2021-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 { GridLayoutInfo } from '../interface';
17import BitSet from './BitSet';
18
19export default class GridLayoutUtil {
20  /**
21   * update GridLayoutInfo
22   *
23   * @param newLayoutRows new layout rows
24   * @param newLayoutColumns new layout columns
25   *
26   * @return new GridLayoutInfo
27   */
28  static updateGridLayoutInfo(gridLayoutInfo: GridLayoutInfo, newLayoutRows: number,
29                              newLayoutColumns: number): GridLayoutInfo {
30    gridLayoutInfo.layoutDescription.pageCount = GridLayoutUtil.updateLayoutInfo(
31      gridLayoutInfo.layoutInfo, newLayoutRows, newLayoutColumns);
32    gridLayoutInfo.layoutDescription.row = newLayoutRows;
33    gridLayoutInfo.layoutDescription.column = newLayoutColumns;
34    return gridLayoutInfo;
35  }
36
37  /**
38   * update layoutInfo
39   *
40   * @param layoutInfo appLayoutInfo List
41   * @param newLayoutRows new layout rows
42   * @param newLayoutColumns new layout columns
43   *
44   * @return new layout pages num
45   */
46  private static updateLayoutInfo(layoutInfo: any, newLayoutRows: number, newLayoutColumns: number): number {
47    let currentPage = -1;
48    let insertPages = 0;
49    const currentPageBitset = new BitSet(newLayoutRows * newLayoutColumns);
50
51    for (let i = 0; i < layoutInfo.length;) {
52      if (currentPage != layoutInfo[i].page) {
53        currentPage = layoutInfo[i].page;
54        currentPageBitset.clear();
55      }
56
57      while (i < layoutInfo.length && layoutInfo[i].page == currentPage) {
58        if (GridLayoutUtil.updatePositionSuccess(layoutInfo[i], currentPageBitset, newLayoutRows, newLayoutColumns, currentPage + insertPages)) {
59          i++;
60        } else {
61          currentPageBitset.clear();
62          insertPages++;
63        }
64      }
65    }
66
67    return currentPage + insertPages + 1;
68  }
69
70  /**
71   * update app position info
72   *
73   * @param appLayout appLayoutInfo List Item
74   * @param currentPageBitset current page bitset
75   * @param layoutRows new layout rows
76   * @param layoutColumns new layout columns
77   * @param currentPage app pages index
78   *
79   * @return whether update success
80   */
81  private static updatePositionSuccess(appLayout: any, currentPageBitset: BitSet,
82    layoutRows: number, layoutColumns: number, currentPage: number): boolean {
83    for (let r = 0; r < layoutRows; r++) {
84      for (let c = 0; c < layoutColumns; c++) {
85        if (!currentPageBitset.get(r * layoutColumns + c)) {
86          appLayout.page = currentPage;
87          appLayout.row = r;
88          appLayout.column = c;
89          currentPageBitset.set(r * layoutColumns + c);
90          return true;
91        }
92      }
93    }
94    return false;
95  }
96}