markdown-it-any-block 3.3.2-beta1 → 3.3.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -45,6 +45,7 @@ async function jsdom_init() {
45
45
  global.HTMLScriptElement = dom.window.HTMLScriptElement;
46
46
  dom.window.scrollTo = () => {
47
47
  };
48
+ global.MutationObserver = dom.window.MutationObserver;
48
49
  }
49
50
  var ABConvert_IOEnum = /* @__PURE__ */ ((ABConvert_IOEnum2) => {
50
51
  ABConvert_IOEnum2["text"] = "string";
@@ -112,61 +113,6 @@ class ABConvert {
112
113
  ABConvertManager.getInstance().list_abConvert.splice(index2, 1);
113
114
  }
114
115
  }
115
- /** --------------------------------- 处理器容器管理 (旧) --------------- */
116
- /*
117
- /// 用户注册处理器
118
- public static registerABProcessor(process: ABProcessorSpec| ABProcessorSpecSimp| ABProcessorSpecUser){
119
- ABConvertManager.getInstance().list_abConvert.push(ABProcessorSpec.registerABProcessor_adapt(process));
120
- }
121
-
122
- public static registerABProcessor_adapt(process: ABProcessorSpec| ABProcessorSpecSimp| ABProcessorSpecUser): ABProcessorSpec{
123
- if ('is_disable' in process) { // 严格版 存储版
124
- return process
125
- }
126
- else if ('process' in process) { // 用户版 注册版
127
- return this.registerABProcessor_adapt_simp(process)
128
- }
129
- else { // 别名版 无代码版
130
- return this.registerABProcessor_adapt_user(process)
131
- }
132
- }
133
-
134
- private static registerABProcessor_adapt_simp(sim: ABProcessorSpecSimp):ABProcessorSpec{
135
- //type t_param = Parameters<typeof sim.process>
136
- //type t_return = ReturnType<typeof sim.process>
137
- const abProcessorSpec: ABProcessorSpec = {
138
- id: sim.id,
139
- name: sim.name,
140
- match: sim.match??sim.id,
141
- default: sim.default??(!sim.match||typeof(sim.match)=="string")?sim.id:null,
142
- detail: sim.detail??"",
143
- process_alias: sim.process_alias??"",
144
- process_param: sim.process_param??null,
145
- process_return: sim.process_return??null,
146
- process: sim.process,
147
- is_disable: false,
148
- register_from: "内置",
149
- }
150
- return abProcessorSpec
151
- }
152
-
153
- private static registerABProcessor_adapt_user(sim: ABProcessorSpecUser):ABProcessorSpec{
154
- const abProcessorSpec: ABProcessorSpec = {
155
- id: sim.id,
156
- name: sim.name,
157
- match: /^\//.test(sim.match)?RegExp(sim.match):sim.match,
158
- default: null,
159
- detail: "",
160
- process_alias: sim.process_alias,
161
- process_param: null,
162
- process_return: null,
163
- process: ()=>{},
164
- is_disable: false,
165
- register_from: "用户",
166
- }
167
- return abProcessorSpec
168
- }
169
- */
170
116
  }
171
117
  const ABReg = {
172
118
  /**
@@ -292,7 +238,10 @@ const ABAlias_json_title = [
292
238
  { regex: /\|heading_140lne\|(fakeList|仿列表)\|/, replacement: "|title2list|list2table|addClass(ab-table-fc)|addClass(ab-table-likelist)|" }
293
239
  ];
294
240
  const ABAlias_json_list = [
295
- { regex: "|listXinline|", replacement: "|list2listdata|listdata2list|" },
241
+ // 特殊
242
+ { regex: "|listXinline|", replacement: "|list2listdata|listdata2strict|listdata2list|" },
243
+ { regex: "|list2task|", replacement: "|list2listdata|listdata2task|listdata2list|" },
244
+ { regex: "|task2", replacement: "|list2listdata|listdata2task|listdata2list|list2" },
296
245
  // list - list&title
297
246
  { regex: /\|list_140lne\|2?(timeline|时间线)\|/, replacement: "|list2timeline|" },
298
247
  { regex: /\|list_140lne\|2?(tabs?|标签页?)\||\|list2tabs?\|/, replacement: "|list2c2listdata|c2listdata2tab|" },
@@ -394,7 +343,7 @@ class ABConvertManager {
394
343
  this.list_abConvert = [];
395
344
  this.m_renderMarkdownFn = (markdown, el) => {
396
345
  el.classList.add("markdown-rendered");
397
- console.error("AnyBlockError: 请先制定/重定义md渲染器");
346
+ console.error("Please use renderMarkdownFn redefine render function");
398
347
  };
399
348
  if (typeof obsidian == "undefined" && typeof app == "undefined") {
400
349
  console.log("[environment]: markdown-it, without obsidian");
@@ -438,7 +387,7 @@ class ABConvertManager {
438
387
  * @param selectorName 选择器名,空表示未知
439
388
  * @return 等于el,无用,后面可以删了
440
389
  */
441
- static autoABConvert(el, header, content, selectorName = "") {
390
+ static autoABConvert(el, header, content, selectorName = "", ctx) {
442
391
  let prev_result = content;
443
392
  let prev_type = "string";
444
393
  let prev_type2 = ABConvert_IOEnum.text;
@@ -453,8 +402,8 @@ class ABConvertManager {
453
402
  {
454
403
  header = autoABAlias(header, selectorName, prev_result);
455
404
  let list_header = header.split("|");
456
- prev_result = this.autoABConvert_runConvert(el, list_header, prev2);
457
- this.autoABConvert_last(el, header, selectorName, prev2);
405
+ prev_result = this.autoABConvert_runConvert(el, list_header, prev2, ctx);
406
+ this.autoABConvert_last(el, header, selectorName, prev2, ctx);
458
407
  }
459
408
  }
460
409
  /**
@@ -466,7 +415,7 @@ class ABConvertManager {
466
415
  * @param prev_type2 上次转换后的结果的类型 (接口声明而来, IOEnum类型)
467
416
  * @returns 递归转换后的结果
468
417
  */
469
- static autoABConvert_runConvert(el, list_header, prev2) {
418
+ static autoABConvert_runConvert(el, list_header, prev2, ctx) {
470
419
  for (let item_header of list_header) {
471
420
  for (let abReplaceProcessor of ABConvertManager.getInstance().list_abConvert) {
472
421
  if (typeof abReplaceProcessor.match == "string") {
@@ -488,7 +437,7 @@ class ABConvertManager {
488
437
  alias = alias.replace(RegExp(`%${i}`), matchs[i]);
489
438
  }
490
439
  })();
491
- prev2.prev_result = this.autoABConvert_runConvert(el, alias.split("|"), prev2);
440
+ prev2.prev_result = this.autoABConvert_runConvert(el, alias.split("|"), prev2, ctx);
492
441
  } else if (abReplaceProcessor.process) {
493
442
  if (abReplaceProcessor.process_param != prev2.prev_type2) {
494
443
  if (abReplaceProcessor.process_param == ABConvert_IOEnum.el && prev2.prev_type2 == ABConvert_IOEnum.text) {
@@ -512,7 +461,7 @@ class ABConvertManager {
512
461
  break;
513
462
  }
514
463
  }
515
- prev2.prev_result = abReplaceProcessor.process(el, item_header, prev2.prev_result);
464
+ prev2.prev_result = abReplaceProcessor.process(el, item_header, prev2.prev_result, ctx);
516
465
  prev2.prev_type = typeof prev2.prev_result;
517
466
  prev2.prev_type2 = abReplaceProcessor.process_return;
518
467
  prev2.prev_processor = abReplaceProcessor.process;
@@ -526,7 +475,7 @@ class ABConvertManager {
526
475
  /**
527
476
  * 子函数,后处理/尾处理,主要进行末尾追加指令
528
477
  */
529
- static autoABConvert_last(el, header, selectorName, prev2) {
478
+ static autoABConvert_last(el, header, selectorName, prev2, ctx) {
530
479
  if (prev2.prev_type == "string" && prev2.prev_type2 == ABConvert_IOEnum.text) {
531
480
  const subEl = document.createElement("div");
532
481
  el.appendChild(subEl);
@@ -856,10 +805,12 @@ class ListProcess {
856
805
  return total_comp;
857
806
  }
858
807
  let list_itemInfo = [];
808
+ let m_line_cache = null;
859
809
  const list_text = text2.split("\n");
860
810
  for (let line of list_text) {
861
811
  const m_line = line.match(ABReg.reg_list_noprefix);
862
812
  if (m_line) {
813
+ m_line_cache = m_line;
863
814
  let list_inline = m_line[4].split(ABReg.inline_split);
864
815
  let level_inline = m_line[1].length;
865
816
  let inline_comp = update_inline_comp(level_inline, list_inline.length - 1);
@@ -872,8 +823,13 @@ class ListProcess {
872
823
  } else {
873
824
  let itemInfo = list_itemInfo.pop();
874
825
  if (itemInfo) {
826
+ if (m_line_cache && /^\s*$/.test(line.slice(0, m_line_cache[1].length + 2))) {
827
+ line = line.slice(m_line_cache[1].length + 2);
828
+ } else {
829
+ line = line.trim();
830
+ }
875
831
  list_itemInfo.push({
876
- content: itemInfo.content + "\n" + line.trim(),
832
+ content: itemInfo.content + "\n" + line,
877
833
  level: itemInfo.level
878
834
  });
879
835
  }
@@ -1147,6 +1103,19 @@ class ListProcess {
1147
1103
  }
1148
1104
  return list_itemInfo2;
1149
1105
  }
1106
+ // 修复任务列表转列表结构后,任务项丢失
1107
+ static data2taskData(list_itemInfo) {
1108
+ for (let item of list_itemInfo) {
1109
+ item.content = item.content.split("\n").map((line) => {
1110
+ const match = line.match(/\[.\] /);
1111
+ if (match) {
1112
+ return "- " + line;
1113
+ }
1114
+ return line;
1115
+ }).join("\n");
1116
+ }
1117
+ return list_itemInfo;
1118
+ }
1150
1119
  /** 二层树转多层一叉树
1151
1120
  * example:
1152
1121
  * - 1
@@ -1186,7 +1155,7 @@ class ListProcess {
1186
1155
  static data2list(list_itemInfo) {
1187
1156
  let list_newcontent = [];
1188
1157
  for (let item of list_itemInfo) {
1189
- const str_indent = " ".repeat(item.level);
1158
+ const str_indent = " ".repeat(item.level);
1190
1159
  let list_content = item.content.split("\n");
1191
1160
  for (let i = 0; i < list_content.length; i++) {
1192
1161
  if (i == 0) list_newcontent.push(str_indent + "- " + list_content[i]);
@@ -1291,11 +1260,21 @@ ABConvert.factory({
1291
1260
  name: "listdata严格化",
1292
1261
  process_param: ABConvert_IOEnum.list_stream,
1293
1262
  process_return: ABConvert_IOEnum.list_stream,
1294
- detail: "将列表数据转化为更规范的列表数据。统一缩进符(2空格 4空格 tab混用)、禁止跳等级(h1直接就到h3)",
1263
+ detail: "将列表数据转化为更规范的列表数据。统一缩进符(2空格 4空格 tab混用)为level 1、禁止跳等级(h1直接就到h3)",
1295
1264
  process: (el, header, content) => {
1296
1265
  return ListProcess.data2strict(content);
1297
1266
  }
1298
1267
  });
1268
+ ABConvert.factory({
1269
+ id: "listdata2task",
1270
+ name: "listdata支持任务列表",
1271
+ process_param: ABConvert_IOEnum.list_stream,
1272
+ process_return: ABConvert_IOEnum.list_stream,
1273
+ detail: "当列表中存在任务列表项时,令此列表项支持任务项",
1274
+ process: (el, header, content) => {
1275
+ return ListProcess.data2taskData(content);
1276
+ }
1277
+ });
1299
1278
  ABConvert.factory({
1300
1279
  id: "list2listnode",
1301
1280
  name: "列表到listnode (beta)",
@@ -1543,72 +1522,72 @@ class C2ListProcess {
1543
1522
  * 两列列表数据转标签栏
1544
1523
  */
1545
1524
  static c2data2tab(list_itemInfo, div, modeT) {
1546
- {
1547
- const tab = document.createElement("div");
1548
- div.appendChild(tab);
1549
- tab.classList.add("ab-tab-root");
1550
- if (modeT) tab.setAttribute("modeT", "true");
1551
- const nav = document.createElement("div");
1552
- tab.appendChild(nav);
1553
- nav.classList.add("ab-tab-nav");
1554
- const content = document.createElement("div");
1555
- tab.appendChild(content);
1556
- content.classList.add("ab-tab-content");
1557
- let current_dom = null;
1558
- for (let i = 0; i < list_itemInfo.length; i++) {
1559
- const itemInfo = list_itemInfo[i];
1560
- if (!current_dom) {
1561
- if (itemInfo.level == 0) {
1562
- const nav_item = document.createElement("button");
1563
- nav.appendChild(nav_item);
1564
- nav_item.classList.add("ab-tab-nav-item");
1565
- nav_item.textContent = itemInfo.content.slice(0, 20);
1566
- nav_item.setAttribute("is_activate", i == 0 ? "true" : "false");
1567
- current_dom = document.createElement("div");
1568
- content.appendChild(current_dom);
1569
- current_dom.classList.add("ab-tab-content-item");
1570
- current_dom.setAttribute("style", i == 0 ? "display:block" : "display:none");
1571
- current_dom.setAttribute("is_activate", i == 0 ? "true" : "false");
1525
+ const tab = document.createElement("div");
1526
+ div.appendChild(tab);
1527
+ tab.classList.add("ab-tab-root");
1528
+ if (modeT) tab.setAttribute("modeT", "true");
1529
+ const nav = document.createElement("div");
1530
+ tab.appendChild(nav);
1531
+ nav.classList.add("ab-tab-nav");
1532
+ const content = document.createElement("div");
1533
+ tab.appendChild(content);
1534
+ content.classList.add("ab-tab-content");
1535
+ let current_dom = null;
1536
+ for (let i = 0; i < list_itemInfo.length; i++) {
1537
+ const item = list_itemInfo[i];
1538
+ if (item.level == 0) {
1539
+ const nav_item = document.createElement("button");
1540
+ nav.appendChild(nav_item);
1541
+ nav_item.classList.add("ab-tab-nav-item");
1542
+ nav_item.setAttribute("is_activate", i == 0 ? "true" : "false");
1543
+ nav_item.setAttribute("data_index", i.toString());
1544
+ nav_item.textContent = item.content.slice(0, 20);
1545
+ current_dom = document.createElement("div");
1546
+ content.appendChild(current_dom);
1547
+ current_dom.classList.add("ab-tab-content-item");
1548
+ current_dom.setAttribute("style", i == 0 ? "display:block" : "display:none");
1549
+ current_dom.setAttribute("is_activate", i == 0 ? "true" : "false");
1550
+ } else if (current_dom) {
1551
+ current_dom.setAttribute("data_index", i.toString());
1552
+ ABConvertManager.getInstance().m_renderMarkdownFn(item.content, current_dom);
1553
+ current_dom = null;
1554
+ } else {
1555
+ continue;
1556
+ }
1557
+ }
1558
+ const lis = tab.querySelectorAll(":scope>.ab-tab-nav>.ab-tab-nav-item");
1559
+ const contents2 = tab.querySelectorAll(":scope>.ab-tab-content>.ab-tab-content-item");
1560
+ if (lis.length != contents2.length) console.warn("ab-tab-nav-item和ab-tab-content-item的数量不一致");
1561
+ for (let i = 0; i < lis.length; i++) {
1562
+ if (ABCSetting.env.startsWith("obsidian")) {
1563
+ lis[i].onclick = () => {
1564
+ for (let j = 0; j < contents2.length; j++) {
1565
+ lis[j].setAttribute("is_activate", "false");
1566
+ contents2[j].setAttribute("is_activate", "false");
1567
+ contents2[j].setAttribute("style", "display:none");
1572
1568
  }
1573
- } else {
1574
- ABConvertManager.getInstance().m_renderMarkdownFn(itemInfo.content, current_dom);
1575
- current_dom = null;
1576
- }
1577
- }
1578
- const lis = tab.querySelectorAll(":scope>.ab-tab-nav>.ab-tab-nav-item");
1579
- const contents2 = tab.querySelectorAll(":scope>.ab-tab-content>.ab-tab-content-item");
1580
- if (lis.length != contents2.length) console.warn("ab-tab-nav-item和ab-tab-content-item的数量不一致");
1581
- for (let i = 0; i < lis.length; i++) {
1582
- if (ABCSetting.env == "obsidian" || ABCSetting.env == "obsidian-min") {
1583
- lis[i].onclick = () => {
1584
- for (let j = 0; j < contents2.length; j++) {
1585
- lis[j].setAttribute("is_activate", "false");
1586
- contents2[j].setAttribute("is_activate", "false");
1587
- contents2[j].setAttribute("style", "display:none");
1588
- }
1589
- lis[i].setAttribute("is_activate", "true");
1590
- contents2[i].setAttribute("is_activate", "true");
1591
- contents2[i].setAttribute("style", "display:block");
1592
- };
1593
- } else {
1594
- lis[i].setAttribute("onclick", `
1595
- const i = ${i}
1596
- const tab_current = this
1597
- const tab_nav = this.parentNode
1598
- const tab_root = tab_nav.parentNode
1599
- const tab_content = tab_root.querySelector(":scope>.ab-tab-content")
1600
- const tab_nav_items = tab_nav.querySelectorAll(":scope>.ab-tab-nav-item")
1601
- const tab_content_items = tab_content.querySelectorAll(":scope>.ab-tab-content-item")
1602
- for (let j=0; j<tab_content_items.length; j++){
1603
- tab_nav_items[j].setAttribute("is_activate", "false")
1604
- tab_content_items[j].setAttribute("is_activate", "false")
1605
- tab_content_items[j].setAttribute("style", "display:none")
1606
- }
1607
- tab_current.setAttribute("is_activate", "true")
1608
- tab_content_items[i].setAttribute("is_activate", "true")
1609
- tab_content_items[i].setAttribute("style", "display:block")
1610
- `);
1611
- }
1569
+ lis[i].setAttribute("is_activate", "true");
1570
+ contents2[i].setAttribute("is_activate", "true");
1571
+ contents2[i].setAttribute("style", "display:block");
1572
+ };
1573
+ } else {
1574
+ lis[i].setAttribute("onclick", `
1575
+ const i = ${i}
1576
+ const tab_current = this
1577
+ const tab_nav = this.parentNode
1578
+ const tab_root = tab_nav.parentNode
1579
+ const tab_content = tab_root.querySelector(":scope>.ab-tab-content")
1580
+ const tab_nav_items = tab_nav.querySelectorAll(":scope>.ab-tab-nav-item")
1581
+ const tab_content_items = tab_content.querySelectorAll(":scope>.ab-tab-content-item")
1582
+ for (let j=0; j<tab_content_items.length; j++){
1583
+ tab_nav_items[j].setAttribute("is_activate", "false")
1584
+ tab_content_items[j].setAttribute("is_activate", "false")
1585
+ tab_content_items[j].setAttribute("style", "display:none")
1586
+ }
1587
+ tab_current.setAttribute("is_activate", "true")
1588
+ tab_content_items[i].setAttribute("is_activate", "true")
1589
+ tab_content_items[i].setAttribute("style", "display:block")
1590
+ `);
1612
1591
  }
1613
1592
  }
1614
1593
  return div;
@@ -1628,12 +1607,13 @@ class C2ListProcess {
1628
1607
  el_item.appendChild(el_title);
1629
1608
  el_title.classList.add("ab-items-title");
1630
1609
  ABConvertManager.getInstance().m_renderMarkdownFn(item.content, el_title);
1631
- } else {
1632
- if (!el_item) continue;
1610
+ } else if (el_item) {
1633
1611
  const el_content = document.createElement("div");
1634
1612
  el_item.appendChild(el_content);
1635
1613
  el_content.classList.add("ab-items-content");
1636
1614
  ABConvertManager.getInstance().m_renderMarkdownFn(item.content, el_content);
1615
+ } else {
1616
+ continue;
1637
1617
  }
1638
1618
  }
1639
1619
  return el;
@@ -2063,7 +2043,7 @@ class DirProcess {
2063
2043
  for (let i = 0; i < l_tr.length; i++) {
2064
2044
  const tr = l_tr[i];
2065
2045
  const targetEl = tr.querySelector(":scope>td:first-child") ?? tr;
2066
- if (ABCSetting.env == "obsidian" || ABCSetting.env == "obsidian-min") {
2046
+ if (ABCSetting.env.startsWith("obsidian")) {
2067
2047
  targetEl.onclick = () => {
2068
2048
  const tr_level = Number(tr.getAttribute("tr_level"));
2069
2049
  if (isNaN(tr_level)) return;
@@ -2094,7 +2074,8 @@ class DirProcess {
2094
2074
  const tr2 = l_tr[j]
2095
2075
  const tr_level2 = Number(tr2.getAttribute("tr_level"))
2096
2076
  if (isNaN(tr_level2)) break
2097
- if (tr_level2<=tr_level) break
2077
+ if (tr_level2 <= tr_level) break // 影响所有后代级
2078
+ // if (tr_level2 != tr_level+1) break // 影响下一级的 (话说这里可能有列表规范性问题?)
2098
2079
  (tr_isfold == "true") ? tr2.style.display = "" : tr2.style.display = "none"
2099
2080
  flag_do_fold = true
2100
2081
  }
@@ -2111,35 +2092,23 @@ class DirProcess {
2111
2092
  const svgStr_unfold = `<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-unfold-vertical-icon lucide-unfold-vertical"><path d="M12 22v-6"/><path d="M12 8V2"/><path d="M4 12H2"/><path d="M10 12H8"/><path d="M16 12h-2"/><path d="M22 12h-2"/><path d="m15 19-3 3-3-3"/><path d="m15 5-3-3-3 3"/></svg>`;
2112
2093
  btn.setAttribute("is_fold", "false");
2113
2094
  btn.innerHTML = svgStr_fold;
2114
- if (ABCSetting.env == "obsidian" || ABCSetting.env == "obsidian-min") {
2095
+ if (ABCSetting.env.startsWith("obsidian")) {
2115
2096
  btn.onclick = () => {
2116
- const l_tr = table.querySelectorAll("tr");
2117
- for (let i = 0; i < l_tr.length; i++) {
2118
- const tr = l_tr[i];
2119
- (() => {
2120
- const tr_level = Number(tr.getAttribute("tr_level"));
2121
- if (isNaN(tr_level)) return;
2122
- const tr_isfold = btn.getAttribute("is_fold");
2123
- if (!tr_isfold) return;
2124
- let flag_do_fold = false;
2125
- for (let j = i + 1; j < l_tr.length; j++) {
2126
- const tr2 = l_tr[j];
2127
- const tr_level2 = Number(tr2.getAttribute("tr_level"));
2128
- if (isNaN(tr_level2)) break;
2129
- if (tr_level2 <= tr_level) break;
2130
- tr_isfold == "true" ? tr2.style.display = "" : tr2.style.display = "none";
2131
- flag_do_fold = true;
2132
- }
2133
- if (flag_do_fold) tr.setAttribute("is_fold", tr_isfold == "true" ? "false" : "true");
2134
- })();
2135
- }
2136
2097
  const is_all_fold = btn.getAttribute("is_fold");
2137
2098
  if (is_all_fold == "true") {
2138
2099
  btn.setAttribute("is_fold", "false");
2139
2100
  btn.innerHTML = svgStr_fold;
2101
+ const btn_subs = table.querySelectorAll("tr[is_fold='true']>td:first-child");
2102
+ btn_subs.forEach((btn_sub) => {
2103
+ btn_sub.click();
2104
+ });
2140
2105
  } else {
2141
2106
  btn.setAttribute("is_fold", "true");
2142
2107
  btn.innerHTML = svgStr_unfold;
2108
+ const btn_subs = table.querySelectorAll("tr[is_fold='false']>td:first-child");
2109
+ btn_subs.forEach((btn_sub) => {
2110
+ btn_sub.click();
2111
+ });
2143
2112
  }
2144
2113
  };
2145
2114
  } else {
@@ -2151,34 +2120,17 @@ class DirProcess {
2151
2120
  const table = btn.parentNode?.querySelector("table");
2152
2121
  if (!table) return;
2153
2122
 
2154
- const l_tr = table.querySelectorAll("tr");
2155
- for (let i=0; i<l_tr.length; i++) {
2156
- const tr = l_tr[i]
2157
- ;(()=>{
2158
- const tr_level = Number(tr.getAttribute("tr_level"))
2159
- if (isNaN(tr_level)) return
2160
- const tr_isfold = btn.getAttribute("is_fold"); // [!code] tr->btn
2161
- if (!tr_isfold) return
2162
- let flag_do_fold = false // 防止折叠最小层
2163
- for (let j=i+1; j<l_tr.length; j++){
2164
- const tr2 = l_tr[j]
2165
- const tr_level2 = Number(tr2.getAttribute("tr_level"))
2166
- if (isNaN(tr_level2)) break
2167
- if (tr_level2<=tr_level) break
2168
- (tr_isfold == "true") ? tr2.style.display = "" : tr2.style.display = "none"
2169
- flag_do_fold = true
2170
- }
2171
- if (flag_do_fold) tr.setAttribute("is_fold", tr_isfold=="true"?"false":"true")
2172
- })()
2173
- }
2174
2123
  const is_all_fold = btn.getAttribute("is_fold")
2175
2124
  if (is_all_fold=="true") {
2176
2125
  btn.setAttribute("is_fold", "false"); btn.innerHTML = svgStr_fold;
2126
+ const btn_subs = table.querySelectorAll("tr[is_fold='true']>td:first-child");
2127
+ btn_subs.forEach((btn_sub) => { btn_sub.click() }) // 注意setAttr版本无断言
2177
2128
  }
2178
2129
  else {
2179
2130
  btn.setAttribute("is_fold", "true"); btn.innerHTML = svgStr_unfold;
2180
- }
2181
- `
2131
+ const btn_subs = table.querySelectorAll("tr[is_fold='false']>td:first-child");
2132
+ btn_subs.forEach((btn_sub) => { btn_sub.click() }) // 注意setAttr版本无断言
2133
+ }`
2182
2134
  );
2183
2135
  }
2184
2136
  }
@@ -2338,7 +2290,7 @@ ABConvert.factory({
2338
2290
  const isListTable = sub_el.classList.contains("ab-list-table-parent");
2339
2291
  const listTable_btn = sub_el.querySelector(".ab-table-fold");
2340
2292
  if (isListTable && listTable_btn) {
2341
- if (ABCSetting.env == "obsidian" || ABCSetting.env == "obsidian-min") {
2293
+ if (ABCSetting.env.startsWith("obsidian")) {
2342
2294
  fn_fold();
2343
2295
  sub_button.textContent = "折叠/展开";
2344
2296
  const fn_fold2 = () => {
@@ -2597,7 +2549,7 @@ ABConvert.factory({
2597
2549
  id: "transposition",
2598
2550
  name: "表格转置",
2599
2551
  match: "transposition",
2600
- detail: "将表格进行转置,就像矩阵转置那样。该版本不支持有跨行跨列单元格",
2552
+ detail: "将表格进行转置,就像矩阵转置那样。该版本不支持有跨行跨列单元格。若复杂表格,请换用trs版本",
2601
2553
  process_param: ABConvert_IOEnum.el,
2602
2554
  process_return: ABConvert_IOEnum.el,
2603
2555
  process: (el, header, content) => {
@@ -2636,72 +2588,21 @@ ABConvert.factory({
2636
2588
  process: (el, header, content) => {
2637
2589
  const origi_table = content.querySelector("table");
2638
2590
  if (!origi_table) return content;
2639
- const origi_rows = origi_table.rows;
2640
- const origi_rowCount = origi_rows.length;
2641
- let origi_colCount = 0;
2642
- for (let relRow = 0; relRow < origi_rowCount; relRow++) {
2643
- let colCount = 0;
2644
- for (const cell of origi_rows[relRow].cells) {
2645
- colCount += cell.colSpan || 1;
2646
- }
2647
- if (colCount > origi_colCount) {
2648
- origi_colCount = colCount;
2649
- }
2650
- }
2651
- const map_table = new Array(origi_rowCount).fill(null).map(() => new Array(origi_colCount).fill(null));
2652
- for (let relRow = 0; relRow < origi_rowCount; relRow++) {
2653
- for (let relCol = 0; relCol < origi_rows[relRow].cells.length; relCol++) {
2654
- const cell = origi_rows[relRow].cells[relCol];
2655
- const rowIndex = relRow;
2656
- let colIndex = relCol;
2657
- while (true) {
2658
- if (colIndex >= map_table[rowIndex].length) {
2659
- console.error("表格解析错误: colIndex超出范围", map_table, rowIndex, colIndex, relRow, relCol);
2660
- return content;
2661
- }
2662
- if (!map_table[rowIndex][colIndex]) {
2663
- break;
2664
- } else colIndex++;
2665
- }
2666
- if (cell.rowSpan > 1) {
2667
- for (let i = 1; i < cell.rowSpan; i++) {
2668
- if (rowIndex + i >= map_table.length) {
2669
- break;
2670
- }
2671
- map_table[rowIndex + i][colIndex] = "^";
2672
- }
2673
- }
2674
- if (cell.colSpan > 1) {
2675
- for (let i = 1; i < cell.rowSpan; i++) {
2676
- if (colIndex + i >= map_table[rowIndex].length) {
2677
- break;
2678
- }
2679
- map_table[rowIndex][colIndex + i] = "<";
2680
- }
2681
- }
2682
- map_table[rowIndex][colIndex] = {
2683
- html: cell,
2684
- rowSpan: cell.rowSpan,
2685
- colSpan: cell.colSpan,
2686
- rowIndex,
2687
- colIndex
2688
- };
2689
- }
2690
- }
2691
- const map_table2 = new Array(origi_colCount).fill(null).map(() => new Array(origi_rowCount).fill(null));
2591
+ let { tableMap, origi_rowCount, origi_colCount } = table2tableMap(origi_table);
2592
+ const tableMap2 = new Array(origi_colCount).fill(null).map(() => new Array(origi_rowCount).fill(null));
2692
2593
  for (let i = 0; i < origi_rowCount; i++) {
2693
2594
  for (let j = 0; j < origi_colCount; j++) {
2694
- const origi_cell = map_table[i][j];
2595
+ const origi_cell = tableMap[i][j];
2695
2596
  if (!origi_cell) continue;
2696
2597
  else if (origi_cell == "<") {
2697
- map_table2[j][i] = "^";
2598
+ tableMap2[j][i] = "^";
2698
2599
  } else if (origi_cell == "^") {
2699
- map_table2[j][i] = "<";
2600
+ tableMap2[j][i] = "<";
2700
2601
  } else {
2701
2602
  let content2 = origi_cell.html;
2702
2603
  if (content2.innerHTML == "<" || content2.innerHTML == "&lt;") content2.innerHTML = "^";
2703
2604
  else if (content2.innerHTML == "^") content2.innerHTML = "<";
2704
- map_table2[j][i] = {
2605
+ tableMap2[j][i] = {
2705
2606
  html: origi_cell.html,
2706
2607
  rowSpan: origi_cell.colSpan || 1,
2707
2608
  colSpan: origi_cell.rowSpan || 1,
@@ -2711,27 +2612,14 @@ ABConvert.factory({
2711
2612
  }
2712
2613
  }
2713
2614
  }
2714
- const trans_table = document.createElement("table");
2715
- origi_table.classList.add("ab-transposition", "ab-table");
2615
+ const tmp = origi_colCount;
2616
+ origi_colCount = origi_rowCount;
2617
+ origi_rowCount = tmp;
2618
+ const trans_table = tableMap2table(tableMap2, origi_rowCount, origi_colCount);
2716
2619
  origi_table.classList.forEach((className) => {
2717
2620
  trans_table.classList.add(className);
2718
2621
  });
2719
- const trans_body = document.createElement("tbody");
2720
- trans_table.appendChild(trans_body);
2721
- for (let i = 0; i < origi_colCount; i++) {
2722
- const newRow = trans_body.insertRow();
2723
- for (let j = 0; j < origi_rowCount; j++) {
2724
- const cell = map_table2[i][j];
2725
- if (!cell) continue;
2726
- if (cell == "<" || cell == "^") continue;
2727
- const newCell = newRow.insertCell();
2728
- newCell.innerHTML = cell.html.innerHTML;
2729
- newCell.rowSpan = cell.rowSpan;
2730
- newCell.colSpan = cell.colSpan;
2731
- newCell.setAttribute("rowIndex", String(cell.rowIndex));
2732
- newCell.setAttribute("colIndex", String(cell.colIndex));
2733
- }
2734
- }
2622
+ trans_table.classList.add("ab-transposition", "ab-table");
2735
2623
  origi_table.innerHTML = trans_table.innerHTML;
2736
2624
  return content;
2737
2625
  }
@@ -2746,53 +2634,107 @@ ABConvert.factory({
2746
2634
  process: (el, header, content) => {
2747
2635
  const origi_table = content.querySelector("table");
2748
2636
  if (!origi_table) return content;
2749
- const origi_rows = origi_table.rows;
2750
- const origi_rowCount = origi_rows.length;
2751
- let origi_colCount = 0;
2637
+ let { tableMap, origi_rowCount, origi_colCount } = table2tableMap(origi_table, true);
2638
+ const map_table2 = tableMap;
2639
+ const trans_table = tableMap2table(map_table2, origi_rowCount, origi_colCount);
2640
+ origi_table.classList.forEach((className) => {
2641
+ trans_table.classList.add(className);
2642
+ });
2643
+ trans_table.classList.add("ab-extable", "ab-table");
2644
+ origi_table.innerHTML = trans_table.innerHTML;
2645
+ return content;
2646
+ }
2647
+ });
2648
+ ABConvert.factory({
2649
+ id: "strictTable",
2650
+ name: "正规化表格",
2651
+ match: "strictTable",
2652
+ detail: "补全表格的尾丢失项,list2table|trs时,可以有效避免bug",
2653
+ process_param: ABConvert_IOEnum.el,
2654
+ process_return: ABConvert_IOEnum.el,
2655
+ process: (el, header, content) => {
2656
+ const origi_table = content.querySelector("table");
2657
+ if (!origi_table) return content;
2658
+ let { tableMap, origi_rowCount, origi_colCount } = table2tableMap(origi_table);
2659
+ for (let i = 0; i < origi_rowCount; i++) {
2660
+ for (let j = 0; j < origi_colCount; j++) {
2661
+ const origi_cell = tableMap[i][j];
2662
+ if (!origi_cell) {
2663
+ tableMap[i][j] = {
2664
+ html: document.createElement("td"),
2665
+ // 空单元格
2666
+ rowSpan: 1,
2667
+ colSpan: 1,
2668
+ rowIndex: i,
2669
+ colIndex: j
2670
+ };
2671
+ }
2672
+ }
2673
+ }
2674
+ const trans_table = tableMap2table(tableMap, origi_rowCount, origi_colCount);
2675
+ origi_table.classList.forEach((className) => {
2676
+ trans_table.classList.add(className);
2677
+ });
2678
+ trans_table.classList.add("ab-extable", "ab-table");
2679
+ origi_table.innerHTML = trans_table.innerHTML;
2680
+ return content;
2681
+ }
2682
+ });
2683
+ function table2tableMap(origi_table, useMergeFlag = false) {
2684
+ const origi_rows = origi_table.rows;
2685
+ let origi_rowCount = origi_rows.length;
2686
+ let origi_colCount = 0;
2687
+ {
2688
+ let map_colCount = [];
2752
2689
  for (let relRow = 0; relRow < origi_rowCount; relRow++) {
2753
- let colCount = 0;
2754
2690
  for (const cell of origi_rows[relRow].cells) {
2755
- colCount += cell.colSpan || 1;
2756
- }
2757
- if (colCount > origi_colCount) {
2758
- origi_colCount = colCount;
2691
+ const colSpan = cell.colSpan || 1;
2692
+ const rowSpan = cell.rowSpan || 1;
2693
+ for (let relRowSpan = relRow; relRowSpan < relRow + rowSpan; relRowSpan++) {
2694
+ if (!map_colCount[relRowSpan]) map_colCount[relRowSpan] = colSpan;
2695
+ else map_colCount[relRowSpan] += colSpan;
2696
+ }
2759
2697
  }
2760
2698
  }
2761
- const map_table = new Array(origi_rowCount).fill(null).map(() => new Array(origi_colCount).fill(null));
2762
- for (let relRow = 0; relRow < origi_rowCount; relRow++) {
2763
- for (let relCol = 0; relCol < origi_rows[relRow].cells.length; relCol++) {
2764
- const cell = origi_rows[relRow].cells[relCol];
2765
- const rowIndex = relRow;
2766
- let colIndex = relCol;
2767
- while (true) {
2768
- if (colIndex >= map_table[rowIndex].length) {
2769
- console.error("表格解析错误: colIndex超出范围", map_table, rowIndex, colIndex, relRow, relCol);
2770
- return content;
2771
- }
2772
- if (!map_table[rowIndex][colIndex]) {
2773
- break;
2774
- } else colIndex++;
2699
+ origi_rowCount = map_colCount.length;
2700
+ origi_colCount = Math.max(...map_colCount);
2701
+ }
2702
+ const tableMap = new Array(origi_rowCount).fill(null).map(() => new Array(origi_colCount).fill(null));
2703
+ for (let relRow = 0; relRow < origi_rowCount; relRow++) {
2704
+ for (let relCol = 0; relCol < origi_rows[relRow].cells.length; relCol++) {
2705
+ const cell = origi_rows[relRow].cells[relCol];
2706
+ const rowIndex = relRow;
2707
+ let colIndex = relCol;
2708
+ while (true) {
2709
+ if (colIndex >= tableMap[rowIndex].length) {
2710
+ console.error(`表格解析错误: colIndex超出范围: [${rowIndex}][${colIndex}] overflow tableMap[${origi_rowCount - 1}][${origi_colCount - 1}]`, tableMap);
2711
+ throw new Error("表格解析错误: colIndex超出范围");
2775
2712
  }
2776
- if (cell.rowSpan > 1) {
2777
- for (let i = 1; i < cell.rowSpan; i++) {
2778
- if (rowIndex + i >= map_table.length) {
2779
- break;
2780
- }
2781
- map_table[rowIndex + i][colIndex] = "^";
2713
+ if (!tableMap[rowIndex][colIndex]) {
2714
+ break;
2715
+ } else colIndex++;
2716
+ }
2717
+ if (cell.rowSpan > 1) {
2718
+ for (let i = 1; i < cell.rowSpan; i++) {
2719
+ if (rowIndex + i >= tableMap.length) {
2720
+ break;
2782
2721
  }
2722
+ tableMap[rowIndex + i][colIndex] = "^";
2783
2723
  }
2784
- if (cell.colSpan > 1) {
2785
- for (let i = 1; i < cell.rowSpan; i++) {
2786
- if (colIndex + i >= map_table[rowIndex].length) {
2787
- break;
2788
- }
2789
- map_table[rowIndex][colIndex + i] = "<";
2724
+ }
2725
+ if (cell.colSpan > 1) {
2726
+ for (let i = 1; i < cell.rowSpan; i++) {
2727
+ if (colIndex + i >= tableMap[rowIndex].length) {
2728
+ break;
2790
2729
  }
2730
+ tableMap[rowIndex][colIndex + i] = "<";
2791
2731
  }
2732
+ }
2733
+ if (useMergeFlag) {
2792
2734
  if (cell.rowSpan == 1 && cell.colSpan == 1 && cell.textContent == "^") {
2793
- map_table[rowIndex][colIndex] = "^";
2735
+ tableMap[rowIndex][colIndex] = "^";
2794
2736
  for (let i = rowIndex - 1; i >= 0; i--) {
2795
- const item = map_table[i][colIndex];
2737
+ const item = tableMap[i][colIndex];
2796
2738
  if (!item) break;
2797
2739
  if (item == "<") break;
2798
2740
  if (item == "^") continue;
@@ -2803,9 +2745,9 @@ ABConvert.factory({
2803
2745
  }
2804
2746
  }
2805
2747
  } else if (cell.rowSpan == 1 && cell.colSpan == 1 && cell.textContent == "<") {
2806
- map_table[rowIndex][colIndex] = "<";
2748
+ tableMap[rowIndex][colIndex] = "<";
2807
2749
  for (let j = colIndex - 1; j >= 0; j--) {
2808
- const item = map_table[rowIndex][j];
2750
+ const item = tableMap[rowIndex][j];
2809
2751
  if (!item) break;
2810
2752
  if (item == "^") break;
2811
2753
  if (item == "<") continue;
@@ -2816,7 +2758,7 @@ ABConvert.factory({
2816
2758
  }
2817
2759
  }
2818
2760
  } else {
2819
- map_table[rowIndex][colIndex] = {
2761
+ tableMap[rowIndex][colIndex] = {
2820
2762
  html: cell,
2821
2763
  rowSpan: cell.rowSpan,
2822
2764
  colSpan: cell.colSpan,
@@ -2824,34 +2766,43 @@ ABConvert.factory({
2824
2766
  colIndex
2825
2767
  };
2826
2768
  }
2769
+ } else {
2770
+ tableMap[rowIndex][colIndex] = {
2771
+ html: cell,
2772
+ rowSpan: cell.rowSpan,
2773
+ colSpan: cell.colSpan,
2774
+ rowIndex,
2775
+ colIndex
2776
+ };
2827
2777
  }
2828
2778
  }
2829
- const map_table2 = map_table;
2830
- const trans_table = document.createElement("table");
2831
- origi_table.classList.add("ab-transposition", "ab-table");
2832
- origi_table.classList.forEach((className) => {
2833
- trans_table.classList.add(className);
2834
- });
2835
- const trans_body = document.createElement("tbody");
2836
- trans_table.appendChild(trans_body);
2837
- for (let i = 0; i < origi_rowCount; i++) {
2838
- const newRow = trans_body.insertRow();
2839
- for (let j = 0; j < origi_colCount; j++) {
2840
- const cell = map_table2[i][j];
2841
- if (!cell) continue;
2842
- if (cell == "<" || cell == "^") continue;
2843
- const newCell = newRow.insertCell();
2844
- newCell.innerHTML = cell.html.innerHTML;
2845
- newCell.rowSpan = cell.rowSpan;
2846
- newCell.colSpan = cell.colSpan;
2847
- newCell.setAttribute("rowIndex", String(cell.rowIndex));
2848
- newCell.setAttribute("colIndex", String(cell.colIndex));
2849
- }
2850
- }
2851
- origi_table.innerHTML = trans_table.innerHTML;
2852
- return content;
2853
2779
  }
2854
- });
2780
+ return {
2781
+ tableMap,
2782
+ origi_rowCount,
2783
+ origi_colCount
2784
+ };
2785
+ }
2786
+ function tableMap2table(tableMap, origi_rowCount, origi_colCount) {
2787
+ const trans_table = document.createElement("table");
2788
+ const trans_body = document.createElement("tbody");
2789
+ trans_table.appendChild(trans_body);
2790
+ for (let i = 0; i < origi_rowCount; i++) {
2791
+ const newRow = trans_body.insertRow();
2792
+ for (let j = 0; j < origi_colCount; j++) {
2793
+ const cell = tableMap[i][j];
2794
+ if (!cell) continue;
2795
+ if (cell == "<" || cell == "^") continue;
2796
+ const newCell = newRow.insertCell();
2797
+ newCell.innerHTML = cell.html.innerHTML;
2798
+ newCell.rowSpan = cell.rowSpan;
2799
+ newCell.colSpan = cell.colSpan;
2800
+ newCell.setAttribute("rowIndex", String(cell.rowIndex));
2801
+ newCell.setAttribute("colIndex", String(cell.colIndex));
2802
+ }
2803
+ }
2804
+ return trans_table;
2805
+ }
2855
2806
  ABConvert.factory({
2856
2807
  id: "faq",
2857
2808
  name: "FAQ",
@@ -2867,7 +2818,7 @@ ABConvert.factory({
2867
2818
  let mode_qa = "";
2868
2819
  let last_content = "";
2869
2820
  for (let line of list_content) {
2870
- const m_line = line.match(/^([a-zA-Z])(: |:)(.*)/);
2821
+ const m_line = line.match(/^([\S]+)(:|:)(.*)/);
2871
2822
  if (!m_line) {
2872
2823
  if (mode_qa) {
2873
2824
  last_content = last_content + "\n" + line;
@@ -7732,8 +7683,9 @@ const KEYWORD_WHILE = "while ";
7732
7683
  const KEYWORD_GROUP = "group ";
7733
7684
  const KEYWORD_PARTITION = "partition ";
7734
7685
  const KEYWORD_LANE = "lane ";
7735
- const KEYWORD_ELSE = "else";
7736
7686
  const KEYWORD_ELIF = "elif ";
7687
+ const KEYWORD_ELSEIF = "else if ";
7688
+ const KEYWORD_ELSE = "else";
7737
7689
  const KEYWORD_DEFAULT = "default";
7738
7690
  const KEYWORD_DEFAULT2 = "case _";
7739
7691
  const KEYWORD_CASE = "case ";
@@ -7778,7 +7730,7 @@ function processBlock(stats, index2, parentLevel) {
7778
7730
  let processed = false;
7779
7731
  for (const [statType, processor] of Object.entries(statementTypes)) {
7780
7732
  if (stat.isStatementOfType(statType)) {
7781
- const { result: processedResult, nextIndex: nextNext } = processor(stats, next2);
7733
+ const { result: processedResult, nextIndex: nextNext } = processor(stats, next2, statType);
7782
7734
  result += processedResult;
7783
7735
  next2 = nextNext;
7784
7736
  processed = true;
@@ -7806,9 +7758,13 @@ function processIfStatement(stats, index2) {
7806
7758
  result += indentContent(result2);
7807
7759
  nextIndex = nextIndex2;
7808
7760
  }
7809
- while (nextIndex < stats.length && stats[nextIndex].level === stat.level && stats[nextIndex].isStatementOfType(KEYWORD_ELIF, KEYWORD_ELSE)) {
7761
+ while (nextIndex < stats.length && stats[nextIndex].level === stat.level && stats[nextIndex].isStatementOfType(KEYWORD_ELIF, KEYWORD_ELSEIF, KEYWORD_ELSE)) {
7810
7762
  const branch = stats[nextIndex];
7811
- if (branch.isStatementOfType(KEYWORD_ELIF)) {
7763
+ if (branch.isStatementOfType(KEYWORD_ELSEIF)) {
7764
+ const condition2 = branch.takeTagOfStat(KEYWORD_ELSEIF);
7765
+ result += `else if(${condition2}) then (yes)
7766
+ `;
7767
+ } else if (branch.isStatementOfType(KEYWORD_ELIF)) {
7812
7768
  const condition2 = branch.takeTagOfStat(KEYWORD_ELIF);
7813
7769
  result += `else if(${condition2}) then (yes)
7814
7770
  `;
@@ -7823,10 +7779,10 @@ function processIfStatement(stats, index2) {
7823
7779
  result += "endif\n";
7824
7780
  return { result, nextIndex };
7825
7781
  }
7826
- function processSwitchStatement(stats, index2) {
7827
- let result = KEYWORD_SWITCH;
7782
+ function processSwitchStatement(stats, index2, statType) {
7783
+ let result = `switch `;
7828
7784
  const stat = stats[index2];
7829
- const condition = stat.takeTagOfStat(KEYWORD_SWITCH);
7785
+ const condition = stat.takeTagOfStat(statType);
7830
7786
  let nextIndex = index2 + 1;
7831
7787
  result += `(${condition})
7832
7788
  `;
@@ -8154,7 +8110,7 @@ async function data2mindmap(list_itemInfo, div) {
8154
8110
  return render_mermaidText(mermaidText, div);
8155
8111
  }
8156
8112
  async function render_mermaidText(mermaidText, div) {
8157
- if ((ABCSetting.env == "obsidian" || ABCSetting.env == "obsidian-min") && ABCSetting.mermaid) {
8113
+ if (ABCSetting.env.startsWith("obsidian") && ABCSetting.mermaid) {
8158
8114
  ABCSetting.mermaid.then(async (mermaid) => {
8159
8115
  const { svg } = await mermaid.render("ab-mermaid-" + getID(), mermaidText);
8160
8116
  div.innerHTML = svg;
@@ -42445,7 +42401,7 @@ ABConvert.factory({
42445
42401
  function list2markmap(markdown, div) {
42446
42402
  const { root: root2, features } = transformer.transform(markdown.trim());
42447
42403
  transformer.getUsedAssets(features);
42448
- if (ABCSetting.env == "obsidian" || ABCSetting.env == "obsidian-min") {
42404
+ if (ABCSetting.env.startsWith("obsidian")) {
42449
42405
  let height_adapt = 30 + markdown.split("\n").length * 15;
42450
42406
  if (height_adapt > 1e3) height_adapt = 1e3;
42451
42407
  const id = Math.random().toString(36).substring(2);