14514f5e3Sopenharmony_ci/*
24514f5e3Sopenharmony_ci * Copyright (c) 2023 Shenzhen Kaihong Digital Industry Development Co., Ltd.
34514f5e3Sopenharmony_ci * Licensed under the Apache License, Version 2.0 (the "License");
44514f5e3Sopenharmony_ci * you may not use this file except in compliance with the License.
54514f5e3Sopenharmony_ci * You may obtain a copy of the License at
64514f5e3Sopenharmony_ci *
74514f5e3Sopenharmony_ci * http://www.apache.org/licenses/LICENSE-2.0
84514f5e3Sopenharmony_ci *
94514f5e3Sopenharmony_ci * Unless required by applicable law or agreed to in writing, software
104514f5e3Sopenharmony_ci * distributed under the License is distributed on an "AS IS" BASIS,
114514f5e3Sopenharmony_ci * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
124514f5e3Sopenharmony_ci * See the License for the specific language governing permissions and
134514f5e3Sopenharmony_ci * limitations under the License.
144514f5e3Sopenharmony_ci */
154514f5e3Sopenharmony_ci
164514f5e3Sopenharmony_ciconst { XTools } = require('../engine/XTools');
174514f5e3Sopenharmony_ciconst { X2DFast } = require('../engine/graphics/X2DFast');
184514f5e3Sopenharmony_ci
194514f5e3Sopenharmony_ciconst INTYPE = {
204514f5e3Sopenharmony_ci  state: 0,
214514f5e3Sopenharmony_ci  depend: 1,
224514f5e3Sopenharmony_ci  value: 2,
234514f5e3Sopenharmony_ci  framestate: 3,
244514f5e3Sopenharmony_ci  root: 4,
254514f5e3Sopenharmony_ci  other: 5,
264514f5e3Sopenharmony_ci};
274514f5e3Sopenharmony_ci
284514f5e3Sopenharmony_ciclass NodeTypeMask {
294514f5e3Sopenharmony_ci  static NONE = 0;
304514f5e3Sopenharmony_ci  static CONTROL = 1 << INTYPE.state;
314514f5e3Sopenharmony_ci  static DEPEND = 1 << INTYPE.depend;
324514f5e3Sopenharmony_ci  static VALUE = 1 << INTYPE.value;
334514f5e3Sopenharmony_ci  static FRAMESTATE = 1 << INTYPE.framestate;
344514f5e3Sopenharmony_ci  static ROOT = 1 << INTYPE.root;
354514f5e3Sopenharmony_ci  static OTHER = 1 << INTYPE.other;
364514f5e3Sopenharmony_ci}
374514f5e3Sopenharmony_ci
384514f5e3Sopenharmony_ciclass IrToPicture {
394514f5e3Sopenharmony_ci  static INVALID_DEEP = -99999;
404514f5e3Sopenharmony_ci  static NODEH = 20;
414514f5e3Sopenharmony_ci  static LINE_TYPE = ['state', 'depend', 'value', 'framestate', 'root'];
424514f5e3Sopenharmony_ci  static nodeType(ir) {
434514f5e3Sopenharmony_ci    if (XTools.CONFIG.OpTypeControl.indexOf(ir.op) >= 0) {
444514f5e3Sopenharmony_ci      return 'control';
454514f5e3Sopenharmony_ci    }
464514f5e3Sopenharmony_ci    if (ir.in[INTYPE.state].length > 0 && XTools.CONFIG.OpNotControl.indexOf(ir.op) === -1) {
474514f5e3Sopenharmony_ci      return 'control';
484514f5e3Sopenharmony_ci    }
494514f5e3Sopenharmony_ci    if (XTools.CONFIG.OpTypeDepend.indexOf(ir.op) >= 0 || ir.in[INTYPE.depend].length > 0) {
504514f5e3Sopenharmony_ci      return 'depend';
514514f5e3Sopenharmony_ci    }
524514f5e3Sopenharmony_ci    if (XTools.CONFIG.OpTypeValue.indexOf(ir.op) >= 0 || ir.in[INTYPE.value].length > 0) {
534514f5e3Sopenharmony_ci      return 'value';
544514f5e3Sopenharmony_ci    }
554514f5e3Sopenharmony_ci    return 'other';
564514f5e3Sopenharmony_ci  }
574514f5e3Sopenharmony_ci  static nodeTypeMask(ir) {
584514f5e3Sopenharmony_ci    let mask = NodeTypeMask.NONE;
594514f5e3Sopenharmony_ci    if (XTools.CONFIG.OpTypeControl.indexOf(ir.op) >= 0) {
604514f5e3Sopenharmony_ci      mask |= NodeTypeMask.CONTROL;
614514f5e3Sopenharmony_ci    }
624514f5e3Sopenharmony_ci    if (ir.in[INTYPE.state].length > 0 && XTools.CONFIG.OpNotControl.indexOf(ir.op) === -1) {
634514f5e3Sopenharmony_ci      mask |= NodeTypeMask.CONTROL;
644514f5e3Sopenharmony_ci    }
654514f5e3Sopenharmony_ci    if (XTools.CONFIG.OpTypeDepend.indexOf(ir.op) >= 0 || ir.in[INTYPE.depend].length > 0) {
664514f5e3Sopenharmony_ci      mask |= NodeTypeMask.DEPEND;
674514f5e3Sopenharmony_ci    }
684514f5e3Sopenharmony_ci    if (XTools.CONFIG.OpTypeValue.indexOf(ir.op) >= 0 || ir.in[INTYPE.value].length > 0) {
694514f5e3Sopenharmony_ci      mask |= NodeTypeMask.VALUE;
704514f5e3Sopenharmony_ci    }
714514f5e3Sopenharmony_ci    if (XTools.CONFIG.OpTypeFrameState.indexOf(ir.op) >= 0 || ir.in[INTYPE.framestate].length > 0) {
724514f5e3Sopenharmony_ci      mask |= NodeTypeMask.FRAMESTATE;
734514f5e3Sopenharmony_ci    }
744514f5e3Sopenharmony_ci    if (XTools.CONFIG.OpTypeCircuitRoot.indexOf(ir.op) >= 0 || ir.in[INTYPE.root].length > 0) {
754514f5e3Sopenharmony_ci      mask |= NodeTypeMask.ROOT;
764514f5e3Sopenharmony_ci    }
774514f5e3Sopenharmony_ci    if (mask === NodeTypeMask.NONE) {
784514f5e3Sopenharmony_ci      mask = NodeTypeMask.OTHER;
794514f5e3Sopenharmony_ci    }
804514f5e3Sopenharmony_ci    return mask;
814514f5e3Sopenharmony_ci  }
824514f5e3Sopenharmony_ci  static isLoopBack(l, nodes) {
834514f5e3Sopenharmony_ci    if (XTools.CONFIG.OpTypeLoopBegin.indexOf(nodes[l.toId].ir.op) >= 0 && l.fromId === nodes[l.toId].ir.in[0][1]) {
844514f5e3Sopenharmony_ci      return true;
854514f5e3Sopenharmony_ci    }
864514f5e3Sopenharmony_ci    if (XTools.CONFIG.OpTypeDependSelector.indexOf(nodes[l.toId].ir.op) >= 0 && l.fromId === nodes[l.toId].ir.in[1][1]) {
874514f5e3Sopenharmony_ci      return true;
884514f5e3Sopenharmony_ci    }
894514f5e3Sopenharmony_ci    if (XTools.CONFIG.OpTypeValueSelector.indexOf(nodes[l.toId].ir.op) >= 0 && l.fromId === nodes[l.toId].ir.in[2][1]) {
904514f5e3Sopenharmony_ci      return true;
914514f5e3Sopenharmony_ci    }
924514f5e3Sopenharmony_ci    return false;
934514f5e3Sopenharmony_ci  }
944514f5e3Sopenharmony_ci  static toPicture(irList, type, isBlock) {
954514f5e3Sopenharmony_ci    let nodes = {};
964514f5e3Sopenharmony_ci    let entry = -1;
974514f5e3Sopenharmony_ci    for (let ir of irList) { //用于生成图的所有节点
984514f5e3Sopenharmony_ci      if (type === 0) { //仅控制流
994514f5e3Sopenharmony_ci        if (this.nodeType(ir) !== 'control') {
1004514f5e3Sopenharmony_ci          continue;
1014514f5e3Sopenharmony_ci        }
1024514f5e3Sopenharmony_ci      }
1034514f5e3Sopenharmony_ci      let name;
1044514f5e3Sopenharmony_ci      if (XTools.CONFIG.OpTypeJsBytecode.indexOf(ir.op) >= 0) {
1054514f5e3Sopenharmony_ci        name = ir.id + ',' + ir.bytecode;
1064514f5e3Sopenharmony_ci      }
1074514f5e3Sopenharmony_ci      else if (ir.typedop) {
1084514f5e3Sopenharmony_ci        name = ir.id + ',' + ir.typedop;
1094514f5e3Sopenharmony_ci      }
1104514f5e3Sopenharmony_ci      else {
1114514f5e3Sopenharmony_ci        name = ir.id + ',' + ir.op;
1124514f5e3Sopenharmony_ci      }
1134514f5e3Sopenharmony_ci      nodes[ir.id] = {
1144514f5e3Sopenharmony_ci        type: this.nodeType(ir),
1154514f5e3Sopenharmony_ci        mask: this.nodeTypeMask(ir),
1164514f5e3Sopenharmony_ci        hide: false,
1174514f5e3Sopenharmony_ci        inCount: 0,
1184514f5e3Sopenharmony_ci        in: [],
1194514f5e3Sopenharmony_ci        inh: {},
1204514f5e3Sopenharmony_ci        outCount: 0,
1214514f5e3Sopenharmony_ci        out: [],
1224514f5e3Sopenharmony_ci        outh: [],
1234514f5e3Sopenharmony_ci        pos: { x: -1, y: -1 },
1244514f5e3Sopenharmony_ci        deep: this.INVALID_DEEP,
1254514f5e3Sopenharmony_ci        name: name,
1264514f5e3Sopenharmony_ci        nameWidth: X2DFast.gi().getTextWidth(name, 14),
1274514f5e3Sopenharmony_ci        ir: ir,
1284514f5e3Sopenharmony_ci      };
1294514f5e3Sopenharmony_ci      if (entry === -1) {
1304514f5e3Sopenharmony_ci        entry = ir.id;
1314514f5e3Sopenharmony_ci      }
1324514f5e3Sopenharmony_ci    }
1334514f5e3Sopenharmony_ci
1344514f5e3Sopenharmony_ci    let lines = [];
1354514f5e3Sopenharmony_ci    let lid = 0;
1364514f5e3Sopenharmony_ci    this.generateLine(nodes, lines, lid);
1374514f5e3Sopenharmony_ci    this.resetPicture(nodes, isBlock);
1384514f5e3Sopenharmony_ci
1394514f5e3Sopenharmony_ci    return {
1404514f5e3Sopenharmony_ci      nodes: nodes,
1414514f5e3Sopenharmony_ci      lines: lines,
1424514f5e3Sopenharmony_ci    };
1434514f5e3Sopenharmony_ci  }
1444514f5e3Sopenharmony_ci  static generateLine(nodes, lines, lid) {
1454514f5e3Sopenharmony_ci    for (let i in nodes) { //生成连接线
1464514f5e3Sopenharmony_ci      let inId = parseInt(i);
1474514f5e3Sopenharmony_ci      for (let inP1 = 0; inP1 < nodes[inId].ir.in.length; inP1++) {
1484514f5e3Sopenharmony_ci        for (let inP2 = 0; inP2 < nodes[inId].ir.in[inP1].length; inP2++) {
1494514f5e3Sopenharmony_ci          let outId = nodes[inId].ir.in[inP1][inP2];
1504514f5e3Sopenharmony_ci          if (outId in nodes) {
1514514f5e3Sopenharmony_ci            let line = {
1524514f5e3Sopenharmony_ci              lid: lid++,
1534514f5e3Sopenharmony_ci              lineType: this.LINE_TYPE[inP1],
1544514f5e3Sopenharmony_ci              inNum: nodes[inId].inCount,
1554514f5e3Sopenharmony_ci              outNum: nodes[outId].outCount,
1564514f5e3Sopenharmony_ci              fromId: outId,
1574514f5e3Sopenharmony_ci              toId: inId,
1584514f5e3Sopenharmony_ci              inP1: inP1,
1594514f5e3Sopenharmony_ci              inP2: inP2,
1604514f5e3Sopenharmony_ci              outP: nodes[outId].ir.out.indexOf(inId),
1614514f5e3Sopenharmony_ci              used: false,
1624514f5e3Sopenharmony_ci            };
1634514f5e3Sopenharmony_ci            nodes[inId].inCount++;
1644514f5e3Sopenharmony_ci            nodes[inId].in.push(line);
1654514f5e3Sopenharmony_ci            nodes[outId].outCount++;
1664514f5e3Sopenharmony_ci            nodes[outId].out.push(line);
1674514f5e3Sopenharmony_ci            lines.push(line);
1684514f5e3Sopenharmony_ci          }
1694514f5e3Sopenharmony_ci        }
1704514f5e3Sopenharmony_ci      }
1714514f5e3Sopenharmony_ci    }
1724514f5e3Sopenharmony_ci  }
1734514f5e3Sopenharmony_ci
1744514f5e3Sopenharmony_ci  static deepTest(n, nodes, isBlock, stack, dist) {
1754514f5e3Sopenharmony_ci    try {
1764514f5e3Sopenharmony_ci      stack.push(n.ir.id);
1774514f5e3Sopenharmony_ci    }
1784514f5e3Sopenharmony_ci    catch (e) {
1794514f5e3Sopenharmony_ci      console.log(1);
1804514f5e3Sopenharmony_ci    }
1814514f5e3Sopenharmony_ci    if (stack.length > Object.keys(nodes).length * 2) {
1824514f5e3Sopenharmony_ci      return true;
1834514f5e3Sopenharmony_ci    }
1844514f5e3Sopenharmony_ci    if (stack.length > 1 && n.ir.id === dist) {
1854514f5e3Sopenharmony_ci      return true;
1864514f5e3Sopenharmony_ci    }
1874514f5e3Sopenharmony_ci    for (let i = 0; i < n.out.length; i++) {
1884514f5e3Sopenharmony_ci      let nout = nodes[n.out[i].toId];
1894514f5e3Sopenharmony_ci      if (n.deep !== this.INVALID_DEEP) {
1904514f5e3Sopenharmony_ci        if (nout.deep === this.INVALID_DEEP) {
1914514f5e3Sopenharmony_ci          nout.deep = n.deep + 1;
1924514f5e3Sopenharmony_ci          if (this.deepTest(nout, nodes, isBlock, stack, dist)) {
1934514f5e3Sopenharmony_ci            return true;
1944514f5e3Sopenharmony_ci          }
1954514f5e3Sopenharmony_ci        }
1964514f5e3Sopenharmony_ci        if (nout.deep <= n.deep) {
1974514f5e3Sopenharmony_ci          if (!this.isLoopBack(n.out[i], nodes) && !isBlock) {
1984514f5e3Sopenharmony_ci            nout.deep = n.deep + 1;
1994514f5e3Sopenharmony_ci            if (this.deepTest(nout, nodes, isBlock, stack, dist)) {
2004514f5e3Sopenharmony_ci              return true;
2014514f5e3Sopenharmony_ci            }
2024514f5e3Sopenharmony_ci          }
2034514f5e3Sopenharmony_ci        }
2044514f5e3Sopenharmony_ci      }
2054514f5e3Sopenharmony_ci    }
2064514f5e3Sopenharmony_ci    stack.pop();
2074514f5e3Sopenharmony_ci    return false;
2084514f5e3Sopenharmony_ci  }
2094514f5e3Sopenharmony_ci  static checkoutLoop(ls) {
2104514f5e3Sopenharmony_ci    console.log(JSON.stringify(ls));
2114514f5e3Sopenharmony_ci    let dicts = {};
2124514f5e3Sopenharmony_ci    for (let l of ls) {
2134514f5e3Sopenharmony_ci      if (!(l in dicts)) {
2144514f5e3Sopenharmony_ci        dicts[l] = 1;
2154514f5e3Sopenharmony_ci      }
2164514f5e3Sopenharmony_ci      else {
2174514f5e3Sopenharmony_ci        dicts[l]++;
2184514f5e3Sopenharmony_ci      }
2194514f5e3Sopenharmony_ci    }
2204514f5e3Sopenharmony_ci    console.log(JSON.stringify(dicts, null, 4));
2214514f5e3Sopenharmony_ci  }
2224514f5e3Sopenharmony_ci  static TEST_LOOP = true;
2234514f5e3Sopenharmony_ci  static resetPicture(nodes, isBlock) {
2244514f5e3Sopenharmony_ci    if (this.TEST_LOOP && Object.keys(nodes).length > 0) {
2254514f5e3Sopenharmony_ci      for (let k in nodes) {
2264514f5e3Sopenharmony_ci        if (k === 0) {
2274514f5e3Sopenharmony_ci          nodes[k].deep = 0;
2284514f5e3Sopenharmony_ci        }
2294514f5e3Sopenharmony_ci        else {
2304514f5e3Sopenharmony_ci          nodes[k].deep = this.INVALID_DEEP;
2314514f5e3Sopenharmony_ci        }
2324514f5e3Sopenharmony_ci      }
2334514f5e3Sopenharmony_ci      let testResult = [];
2344514f5e3Sopenharmony_ci      this.deepTest(nodes[0], nodes, isBlock, testResult, 0);
2354514f5e3Sopenharmony_ci      if (testResult.length > 0) {
2364514f5e3Sopenharmony_ci        this.checkoutLoop(testResult);
2374514f5e3Sopenharmony_ci      }
2384514f5e3Sopenharmony_ci    }
2394514f5e3Sopenharmony_ci
2404514f5e3Sopenharmony_ci    let entry = true;
2414514f5e3Sopenharmony_ci    let enums = [];
2424514f5e3Sopenharmony_ci    for (let k in nodes) {
2434514f5e3Sopenharmony_ci      let n = nodes[k];
2444514f5e3Sopenharmony_ci      if (n.hide) {
2454514f5e3Sopenharmony_ci        continue;
2464514f5e3Sopenharmony_ci      }
2474514f5e3Sopenharmony_ci      if (entry) {
2484514f5e3Sopenharmony_ci        n.pos.x = 0;
2494514f5e3Sopenharmony_ci        n.pos.y = 0;
2504514f5e3Sopenharmony_ci        n.deep = 0;
2514514f5e3Sopenharmony_ci        entry = false;
2524514f5e3Sopenharmony_ci        enums.push(k);
2534514f5e3Sopenharmony_ci      }
2544514f5e3Sopenharmony_ci      else {
2554514f5e3Sopenharmony_ci        n.deep = this.INVALID_DEEP;
2564514f5e3Sopenharmony_ci      }
2574514f5e3Sopenharmony_ci    }
2584514f5e3Sopenharmony_ci    let collectDebug = [];
2594514f5e3Sopenharmony_ci    while (enums.length > 0) { //12,18,27,28,31,34
2604514f5e3Sopenharmony_ci      let nextenums = [];
2614514f5e3Sopenharmony_ci      for (let e = 0; e < enums.length; e++) {
2624514f5e3Sopenharmony_ci        let k = enums[e];
2634514f5e3Sopenharmony_ci        let n = nodes[k];
2644514f5e3Sopenharmony_ci        if (n.hide) {
2654514f5e3Sopenharmony_ci          continue;
2664514f5e3Sopenharmony_ci        }
2674514f5e3Sopenharmony_ci        for (let i = 0; i < n.out.length; i++) {
2684514f5e3Sopenharmony_ci          let nout = nodes[n.out[i].toId];
2694514f5e3Sopenharmony_ci          if (n.deep !== this.INVALID_DEEP) {
2704514f5e3Sopenharmony_ci            if (nout.deep === this.INVALID_DEEP) {
2714514f5e3Sopenharmony_ci              nout.deep = n.deep + 1;
2724514f5e3Sopenharmony_ci              nextenums.push(nout.ir.id);
2734514f5e3Sopenharmony_ci            }
2744514f5e3Sopenharmony_ci            if (nout.deep <= n.deep) {
2754514f5e3Sopenharmony_ci              if (!this.isLoopBack(n.out[i], nodes) && !isBlock) {
2764514f5e3Sopenharmony_ci                nout.deep = n.deep + 1;
2774514f5e3Sopenharmony_ci                nextenums.push(nout.ir.id);
2784514f5e3Sopenharmony_ci              }
2794514f5e3Sopenharmony_ci            }
2804514f5e3Sopenharmony_ci          }
2814514f5e3Sopenharmony_ci        }
2824514f5e3Sopenharmony_ci        for (let i = 0; i < n.in.length; i++) {
2834514f5e3Sopenharmony_ci          let nin = nodes[n.in[i].fromId];
2844514f5e3Sopenharmony_ci          if (n.deep !== this.INVALID_DEEP) {
2854514f5e3Sopenharmony_ci            if (nin.deep === this.INVALID_DEEP) {
2864514f5e3Sopenharmony_ci              nin.deep = n.deep - 1;
2874514f5e3Sopenharmony_ci              nextenums.push(nin.ir.id);
2884514f5e3Sopenharmony_ci            }
2894514f5e3Sopenharmony_ci            if (nin.deep >= n.deep) {
2904514f5e3Sopenharmony_ci              if (!this.isLoopBack(n.in[i], nodes) && !isBlock) {
2914514f5e3Sopenharmony_ci                n.deep = nin.deep + 1;
2924514f5e3Sopenharmony_ci                nextenums.push(n.ir.id);
2934514f5e3Sopenharmony_ci              }
2944514f5e3Sopenharmony_ci            }
2954514f5e3Sopenharmony_ci          }
2964514f5e3Sopenharmony_ci        }
2974514f5e3Sopenharmony_ci      }
2984514f5e3Sopenharmony_ci      collectDebug.push(enums);
2994514f5e3Sopenharmony_ci
3004514f5e3Sopenharmony_ci      enums = nextenums;
3014514f5e3Sopenharmony_ci    }
3024514f5e3Sopenharmony_ci
3034514f5e3Sopenharmony_ci    let levels = {};
3044514f5e3Sopenharmony_ci    for (let k in nodes) { //节点分层
3054514f5e3Sopenharmony_ci      let n = nodes[k];
3064514f5e3Sopenharmony_ci      if (n.hide) {
3074514f5e3Sopenharmony_ci        continue;
3084514f5e3Sopenharmony_ci      }
3094514f5e3Sopenharmony_ci      if (!(n.deep in levels)) {
3104514f5e3Sopenharmony_ci        levels[n.deep] = [];
3114514f5e3Sopenharmony_ci      }
3124514f5e3Sopenharmony_ci      levels[n.deep].push(n);
3134514f5e3Sopenharmony_ci    }
3144514f5e3Sopenharmony_ci    let ty = 50;
3154514f5e3Sopenharmony_ci    for (let k in nodes) {
3164514f5e3Sopenharmony_ci      let n = nodes[k];
3174514f5e3Sopenharmony_ci      let ltypes = [];
3184514f5e3Sopenharmony_ci      for (let l of n.out) {
3194514f5e3Sopenharmony_ci        if (ltypes.indexOf(l.lineType) < 0) {
3204514f5e3Sopenharmony_ci          ltypes.push(l.lineType);
3214514f5e3Sopenharmony_ci        }
3224514f5e3Sopenharmony_ci      }
3234514f5e3Sopenharmony_ci      n.ltypes = ltypes;
3244514f5e3Sopenharmony_ci      if (n.hide) {
3254514f5e3Sopenharmony_ci        continue;
3264514f5e3Sopenharmony_ci      }
3274514f5e3Sopenharmony_ci      if (n.deep === this.INVALID_DEEP) {
3284514f5e3Sopenharmony_ci        n.pos.x = this.INVALID_DEEP; //Scr.logicw - 100;
3294514f5e3Sopenharmony_ci        n.pos.y = ty;
3304514f5e3Sopenharmony_ci        ty += 50;
3314514f5e3Sopenharmony_ci      }
3324514f5e3Sopenharmony_ci    }
3334514f5e3Sopenharmony_ci    let posy = 0;
3344514f5e3Sopenharmony_ci    let ks = Object.keys(levels).sort((a, b) => { return parseInt(a) - parseInt(b) });
3354514f5e3Sopenharmony_ci    for (let k of ks) {
3364514f5e3Sopenharmony_ci      k = parseInt(k);
3374514f5e3Sopenharmony_ci      if (k === this.INVALID_DEEP) {
3384514f5e3Sopenharmony_ci        continue;
3394514f5e3Sopenharmony_ci      }
3404514f5e3Sopenharmony_ci      let inCount = 0;
3414514f5e3Sopenharmony_ci      let outCount = 0;
3424514f5e3Sopenharmony_ci      let inP = 0;
3434514f5e3Sopenharmony_ci      for (let i = 0; i < levels[k].length; i++) {
3444514f5e3Sopenharmony_ci        let n = levels[k];
3454514f5e3Sopenharmony_ci        if (n.hide) {
3464514f5e3Sopenharmony_ci          continue;
3474514f5e3Sopenharmony_ci        }
3484514f5e3Sopenharmony_ci        for (let j = 0; j < n[i].in.length; j++) {
3494514f5e3Sopenharmony_ci          let l = n[i].in[j];
3504514f5e3Sopenharmony_ci          if (!n[i].inh[l.fromId + l.lineType]) {
3514514f5e3Sopenharmony_ci            n[i].inh[l.fromId + l.lineType] = (inP + 1) * 5;
3524514f5e3Sopenharmony_ci            inP += 1;
3534514f5e3Sopenharmony_ci          }
3544514f5e3Sopenharmony_ci        }
3554514f5e3Sopenharmony_ci        inCount += Object.keys(n[i].inh).length;
3564514f5e3Sopenharmony_ci
3574514f5e3Sopenharmony_ci        outCount += n[i].ltypes.length;
3584514f5e3Sopenharmony_ci      }
3594514f5e3Sopenharmony_ci      posy += (inCount + 1) * 5;
3604514f5e3Sopenharmony_ci
3614514f5e3Sopenharmony_ci      let outP = 0;
3624514f5e3Sopenharmony_ci      for (let i = 0; i < levels[k].length; i++) {
3634514f5e3Sopenharmony_ci        let n = levels[k];
3644514f5e3Sopenharmony_ci        if (n.hide) {
3654514f5e3Sopenharmony_ci          continue;
3664514f5e3Sopenharmony_ci        }
3674514f5e3Sopenharmony_ci        for (let j = 0; j < n[i].out.length; j++) {
3684514f5e3Sopenharmony_ci          n[i].outh[j] = (outP + 1 + n[i].ltypes.indexOf(n[i].out[j].lineType)) * 5;
3694514f5e3Sopenharmony_ci        }
3704514f5e3Sopenharmony_ci        n[i].pos.y = posy;
3714514f5e3Sopenharmony_ci        outP += n[i].ltypes.length;
3724514f5e3Sopenharmony_ci      }
3734514f5e3Sopenharmony_ci
3744514f5e3Sopenharmony_ci      posy += (outCount + 1) * 5 + this.NODEH;
3754514f5e3Sopenharmony_ci
3764514f5e3Sopenharmony_ci      let w = 0;
3774514f5e3Sopenharmony_ci      for (let i = 0; i < levels[k].length; i++) { //当前行总宽度
3784514f5e3Sopenharmony_ci        w += levels[k][i].nameWidth + 20;
3794514f5e3Sopenharmony_ci      }
3804514f5e3Sopenharmony_ci      let x = -w / 2;
3814514f5e3Sopenharmony_ci      for (let i = 0; i < levels[k].length; i++) { //每个节点x偏移
3824514f5e3Sopenharmony_ci        levels[k][i].pos.x = x + 10;
3834514f5e3Sopenharmony_ci        x += levels[k][i].nameWidth + 20;
3844514f5e3Sopenharmony_ci      }
3854514f5e3Sopenharmony_ci    }
3864514f5e3Sopenharmony_ci  }
3874514f5e3Sopenharmony_ci}
3884514f5e3Sopenharmony_ci
3894514f5e3Sopenharmony_cimodule.exports = {
3904514f5e3Sopenharmony_ci  IrToPicture
3914514f5e3Sopenharmony_ci};