xfa_object.js 29 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214
  1. /**
  2. * @licstart The following is the entire license notice for the
  3. * Javascript code in this page
  4. *
  5. * Copyright 2022 Mozilla Foundation
  6. *
  7. * Licensed under the Apache License, Version 2.0 (the "License");
  8. * you may not use this file except in compliance with the License.
  9. * You may obtain a copy of the License at
  10. *
  11. * http://www.apache.org/licenses/LICENSE-2.0
  12. *
  13. * Unless required by applicable law or agreed to in writing, software
  14. * distributed under the License is distributed on an "AS IS" BASIS,
  15. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  16. * See the License for the specific language governing permissions and
  17. * limitations under the License.
  18. *
  19. * @licend The above is the entire license notice for the
  20. * Javascript code in this page
  21. */
  22. "use strict";
  23. Object.defineProperty(exports, "__esModule", {
  24. value: true
  25. });
  26. exports.XmlObject = exports.XFAObjectArray = exports.XFAObject = exports.XFAAttribute = exports.StringObject = exports.OptionObject = exports.Option10 = exports.Option01 = exports.IntegerObject = exports.ContentObject = exports.$uid = exports.$toStyle = exports.$toString = exports.$toPages = exports.$toHTML = exports.$text = exports.$tabIndex = exports.$setValue = exports.$setSetAttributes = exports.$setId = exports.$searchNode = exports.$root = exports.$resolvePrototypes = exports.$removeChild = exports.$pushPara = exports.$pushGlyphs = exports.$popPara = exports.$onText = exports.$onChildCheck = exports.$onChild = exports.$nsAttributes = exports.$nodeName = exports.$namespaceId = exports.$isUsable = exports.$isTransparent = exports.$isThereMoreWidth = exports.$isSplittable = exports.$isNsAgnostic = exports.$isDescendent = exports.$isDataValue = exports.$isCDATAXml = exports.$isBindable = exports.$insertAt = exports.$indexOf = exports.$ids = exports.$hasSettableValue = exports.$globalData = exports.$getTemplateRoot = exports.$getSubformParent = exports.$getRealChildrenByNameIt = exports.$getParent = exports.$getNextPage = exports.$getExtra = exports.$getDataValue = exports.$getContainedChildren = exports.$getChildrenByNameIt = exports.$getChildrenByName = exports.$getChildrenByClass = exports.$getChildren = exports.$getAvailableSpace = exports.$getAttributes = exports.$getAttributeIt = exports.$flushHTML = exports.$finalize = exports.$extra = exports.$dump = exports.$data = exports.$content = exports.$consumed = exports.$clone = exports.$cleanup = exports.$cleanPage = exports.$clean = exports.$childrenToHTML = exports.$appendChild = exports.$addHTML = exports.$acceptWhitespace = void 0;
  27. var _utils = require("./utils.js");
  28. var _util = require("../../shared/util.js");
  29. var _core_utils = require("../core_utils.js");
  30. var _namespaces = require("./namespaces.js");
  31. var _som = require("./som.js");
  32. const $acceptWhitespace = Symbol();
  33. exports.$acceptWhitespace = $acceptWhitespace;
  34. const $addHTML = Symbol();
  35. exports.$addHTML = $addHTML;
  36. const $appendChild = Symbol();
  37. exports.$appendChild = $appendChild;
  38. const $childrenToHTML = Symbol();
  39. exports.$childrenToHTML = $childrenToHTML;
  40. const $clean = Symbol();
  41. exports.$clean = $clean;
  42. const $cleanPage = Symbol();
  43. exports.$cleanPage = $cleanPage;
  44. const $cleanup = Symbol();
  45. exports.$cleanup = $cleanup;
  46. const $clone = Symbol();
  47. exports.$clone = $clone;
  48. const $consumed = Symbol();
  49. exports.$consumed = $consumed;
  50. const $content = Symbol("content");
  51. exports.$content = $content;
  52. const $data = Symbol("data");
  53. exports.$data = $data;
  54. const $dump = Symbol();
  55. exports.$dump = $dump;
  56. const $extra = Symbol("extra");
  57. exports.$extra = $extra;
  58. const $finalize = Symbol();
  59. exports.$finalize = $finalize;
  60. const $flushHTML = Symbol();
  61. exports.$flushHTML = $flushHTML;
  62. const $getAttributeIt = Symbol();
  63. exports.$getAttributeIt = $getAttributeIt;
  64. const $getAttributes = Symbol();
  65. exports.$getAttributes = $getAttributes;
  66. const $getAvailableSpace = Symbol();
  67. exports.$getAvailableSpace = $getAvailableSpace;
  68. const $getChildrenByClass = Symbol();
  69. exports.$getChildrenByClass = $getChildrenByClass;
  70. const $getChildrenByName = Symbol();
  71. exports.$getChildrenByName = $getChildrenByName;
  72. const $getChildrenByNameIt = Symbol();
  73. exports.$getChildrenByNameIt = $getChildrenByNameIt;
  74. const $getDataValue = Symbol();
  75. exports.$getDataValue = $getDataValue;
  76. const $getExtra = Symbol();
  77. exports.$getExtra = $getExtra;
  78. const $getRealChildrenByNameIt = Symbol();
  79. exports.$getRealChildrenByNameIt = $getRealChildrenByNameIt;
  80. const $getChildren = Symbol();
  81. exports.$getChildren = $getChildren;
  82. const $getContainedChildren = Symbol();
  83. exports.$getContainedChildren = $getContainedChildren;
  84. const $getNextPage = Symbol();
  85. exports.$getNextPage = $getNextPage;
  86. const $getSubformParent = Symbol();
  87. exports.$getSubformParent = $getSubformParent;
  88. const $getParent = Symbol();
  89. exports.$getParent = $getParent;
  90. const $getTemplateRoot = Symbol();
  91. exports.$getTemplateRoot = $getTemplateRoot;
  92. const $globalData = Symbol();
  93. exports.$globalData = $globalData;
  94. const $hasSettableValue = Symbol();
  95. exports.$hasSettableValue = $hasSettableValue;
  96. const $ids = Symbol();
  97. exports.$ids = $ids;
  98. const $indexOf = Symbol();
  99. exports.$indexOf = $indexOf;
  100. const $insertAt = Symbol();
  101. exports.$insertAt = $insertAt;
  102. const $isCDATAXml = Symbol();
  103. exports.$isCDATAXml = $isCDATAXml;
  104. const $isBindable = Symbol();
  105. exports.$isBindable = $isBindable;
  106. const $isDataValue = Symbol();
  107. exports.$isDataValue = $isDataValue;
  108. const $isDescendent = Symbol();
  109. exports.$isDescendent = $isDescendent;
  110. const $isNsAgnostic = Symbol();
  111. exports.$isNsAgnostic = $isNsAgnostic;
  112. const $isSplittable = Symbol();
  113. exports.$isSplittable = $isSplittable;
  114. const $isThereMoreWidth = Symbol();
  115. exports.$isThereMoreWidth = $isThereMoreWidth;
  116. const $isTransparent = Symbol();
  117. exports.$isTransparent = $isTransparent;
  118. const $isUsable = Symbol();
  119. exports.$isUsable = $isUsable;
  120. const $lastAttribute = Symbol();
  121. const $namespaceId = Symbol("namespaceId");
  122. exports.$namespaceId = $namespaceId;
  123. const $nodeName = Symbol("nodeName");
  124. exports.$nodeName = $nodeName;
  125. const $nsAttributes = Symbol();
  126. exports.$nsAttributes = $nsAttributes;
  127. const $onChild = Symbol();
  128. exports.$onChild = $onChild;
  129. const $onChildCheck = Symbol();
  130. exports.$onChildCheck = $onChildCheck;
  131. const $onText = Symbol();
  132. exports.$onText = $onText;
  133. const $pushGlyphs = Symbol();
  134. exports.$pushGlyphs = $pushGlyphs;
  135. const $popPara = Symbol();
  136. exports.$popPara = $popPara;
  137. const $pushPara = Symbol();
  138. exports.$pushPara = $pushPara;
  139. const $removeChild = Symbol();
  140. exports.$removeChild = $removeChild;
  141. const $root = Symbol("root");
  142. exports.$root = $root;
  143. const $resolvePrototypes = Symbol();
  144. exports.$resolvePrototypes = $resolvePrototypes;
  145. const $searchNode = Symbol();
  146. exports.$searchNode = $searchNode;
  147. const $setId = Symbol();
  148. exports.$setId = $setId;
  149. const $setSetAttributes = Symbol();
  150. exports.$setSetAttributes = $setSetAttributes;
  151. const $setValue = Symbol();
  152. exports.$setValue = $setValue;
  153. const $tabIndex = Symbol();
  154. exports.$tabIndex = $tabIndex;
  155. const $text = Symbol();
  156. exports.$text = $text;
  157. const $toPages = Symbol();
  158. exports.$toPages = $toPages;
  159. const $toHTML = Symbol();
  160. exports.$toHTML = $toHTML;
  161. const $toString = Symbol();
  162. exports.$toString = $toString;
  163. const $toStyle = Symbol();
  164. exports.$toStyle = $toStyle;
  165. const $uid = Symbol("uid");
  166. exports.$uid = $uid;
  167. const _applyPrototype = Symbol();
  168. const _attributes = Symbol();
  169. const _attributeNames = Symbol();
  170. const _children = Symbol("_children");
  171. const _cloneAttribute = Symbol();
  172. const _dataValue = Symbol();
  173. const _defaultValue = Symbol();
  174. const _filteredChildrenGenerator = Symbol();
  175. const _getPrototype = Symbol();
  176. const _getUnsetAttributes = Symbol();
  177. const _hasChildren = Symbol();
  178. const _max = Symbol();
  179. const _options = Symbol();
  180. const _parent = Symbol("parent");
  181. const _resolvePrototypesHelper = Symbol();
  182. const _setAttributes = Symbol();
  183. const _validator = Symbol();
  184. let uid = 0;
  185. const NS_DATASETS = _namespaces.NamespaceIds.datasets.id;
  186. class XFAObject {
  187. constructor(nsId, name, hasChildren = false) {
  188. this[$namespaceId] = nsId;
  189. this[$nodeName] = name;
  190. this[_hasChildren] = hasChildren;
  191. this[_parent] = null;
  192. this[_children] = [];
  193. this[$uid] = `${name}${uid++}`;
  194. this[$globalData] = null;
  195. }
  196. [$onChild](child) {
  197. if (!this[_hasChildren] || !this[$onChildCheck](child)) {
  198. return false;
  199. }
  200. const name = child[$nodeName];
  201. const node = this[name];
  202. if (node instanceof XFAObjectArray) {
  203. if (node.push(child)) {
  204. this[$appendChild](child);
  205. return true;
  206. }
  207. } else {
  208. if (node !== null) {
  209. this[$removeChild](node);
  210. }
  211. this[name] = child;
  212. this[$appendChild](child);
  213. return true;
  214. }
  215. let id = "";
  216. if (this.id) {
  217. id = ` (id: ${this.id})`;
  218. } else if (this.name) {
  219. id = ` (name: ${this.name} ${this.h.value})`;
  220. }
  221. (0, _util.warn)(`XFA - node "${this[$nodeName]}"${id} has already enough "${name}"!`);
  222. return false;
  223. }
  224. [$onChildCheck](child) {
  225. return this.hasOwnProperty(child[$nodeName]) && child[$namespaceId] === this[$namespaceId];
  226. }
  227. [$isNsAgnostic]() {
  228. return false;
  229. }
  230. [$acceptWhitespace]() {
  231. return false;
  232. }
  233. [$isCDATAXml]() {
  234. return false;
  235. }
  236. [$isBindable]() {
  237. return false;
  238. }
  239. [$popPara]() {
  240. if (this.para) {
  241. this[$getTemplateRoot]()[$extra].paraStack.pop();
  242. }
  243. }
  244. [$pushPara]() {
  245. this[$getTemplateRoot]()[$extra].paraStack.push(this.para);
  246. }
  247. [$setId](ids) {
  248. if (this.id && this[$namespaceId] === _namespaces.NamespaceIds.template.id) {
  249. ids.set(this.id, this);
  250. }
  251. }
  252. [$getTemplateRoot]() {
  253. return this[$globalData].template;
  254. }
  255. [$isSplittable]() {
  256. return false;
  257. }
  258. [$isThereMoreWidth]() {
  259. return false;
  260. }
  261. [$appendChild](child) {
  262. child[_parent] = this;
  263. this[_children].push(child);
  264. if (!child[$globalData] && this[$globalData]) {
  265. child[$globalData] = this[$globalData];
  266. }
  267. }
  268. [$removeChild](child) {
  269. const i = this[_children].indexOf(child);
  270. this[_children].splice(i, 1);
  271. }
  272. [$hasSettableValue]() {
  273. return this.hasOwnProperty("value");
  274. }
  275. [$setValue](_) {}
  276. [$onText](_) {}
  277. [$finalize]() {}
  278. [$clean](builder) {
  279. delete this[_hasChildren];
  280. if (this[$cleanup]) {
  281. builder.clean(this[$cleanup]);
  282. delete this[$cleanup];
  283. }
  284. }
  285. [$indexOf](child) {
  286. return this[_children].indexOf(child);
  287. }
  288. [$insertAt](i, child) {
  289. child[_parent] = this;
  290. this[_children].splice(i, 0, child);
  291. if (!child[$globalData] && this[$globalData]) {
  292. child[$globalData] = this[$globalData];
  293. }
  294. }
  295. [$isTransparent]() {
  296. return !this.name;
  297. }
  298. [$lastAttribute]() {
  299. return "";
  300. }
  301. [$text]() {
  302. if (this[_children].length === 0) {
  303. return this[$content];
  304. }
  305. return this[_children].map(c => c[$text]()).join("");
  306. }
  307. get [_attributeNames]() {
  308. const proto = Object.getPrototypeOf(this);
  309. if (!proto._attributes) {
  310. const attributes = proto._attributes = new Set();
  311. for (const name of Object.getOwnPropertyNames(this)) {
  312. if (this[name] === null || this[name] instanceof XFAObject || this[name] instanceof XFAObjectArray) {
  313. break;
  314. }
  315. attributes.add(name);
  316. }
  317. }
  318. return (0, _util.shadow)(this, _attributeNames, proto._attributes);
  319. }
  320. [$isDescendent](parent) {
  321. let node = this;
  322. while (node) {
  323. if (node === parent) {
  324. return true;
  325. }
  326. node = node[$getParent]();
  327. }
  328. return false;
  329. }
  330. [$getParent]() {
  331. return this[_parent];
  332. }
  333. [$getSubformParent]() {
  334. return this[$getParent]();
  335. }
  336. [$getChildren](name = null) {
  337. if (!name) {
  338. return this[_children];
  339. }
  340. return this[name];
  341. }
  342. [$dump]() {
  343. const dumped = Object.create(null);
  344. if (this[$content]) {
  345. dumped.$content = this[$content];
  346. }
  347. for (const name of Object.getOwnPropertyNames(this)) {
  348. const value = this[name];
  349. if (value === null) {
  350. continue;
  351. }
  352. if (value instanceof XFAObject) {
  353. dumped[name] = value[$dump]();
  354. } else if (value instanceof XFAObjectArray) {
  355. if (!value.isEmpty()) {
  356. dumped[name] = value.dump();
  357. }
  358. } else {
  359. dumped[name] = value;
  360. }
  361. }
  362. return dumped;
  363. }
  364. [$toStyle]() {
  365. return null;
  366. }
  367. [$toHTML]() {
  368. return _utils.HTMLResult.EMPTY;
  369. }
  370. *[$getContainedChildren]() {
  371. for (const node of this[$getChildren]()) {
  372. yield node;
  373. }
  374. }
  375. *[_filteredChildrenGenerator](filter, include) {
  376. for (const node of this[$getContainedChildren]()) {
  377. if (!filter || include === filter.has(node[$nodeName])) {
  378. const availableSpace = this[$getAvailableSpace]();
  379. const res = node[$toHTML](availableSpace);
  380. if (!res.success) {
  381. this[$extra].failingNode = node;
  382. }
  383. yield res;
  384. }
  385. }
  386. }
  387. [$flushHTML]() {
  388. return null;
  389. }
  390. [$addHTML](html, bbox) {
  391. this[$extra].children.push(html);
  392. }
  393. [$getAvailableSpace]() {}
  394. [$childrenToHTML]({
  395. filter = null,
  396. include = true
  397. }) {
  398. if (!this[$extra].generator) {
  399. this[$extra].generator = this[_filteredChildrenGenerator](filter, include);
  400. } else {
  401. const availableSpace = this[$getAvailableSpace]();
  402. const res = this[$extra].failingNode[$toHTML](availableSpace);
  403. if (!res.success) {
  404. return res;
  405. }
  406. if (res.html) {
  407. this[$addHTML](res.html, res.bbox);
  408. }
  409. delete this[$extra].failingNode;
  410. }
  411. while (true) {
  412. const gen = this[$extra].generator.next();
  413. if (gen.done) {
  414. break;
  415. }
  416. const res = gen.value;
  417. if (!res.success) {
  418. return res;
  419. }
  420. if (res.html) {
  421. this[$addHTML](res.html, res.bbox);
  422. }
  423. }
  424. this[$extra].generator = null;
  425. return _utils.HTMLResult.EMPTY;
  426. }
  427. [$setSetAttributes](attributes) {
  428. this[_setAttributes] = new Set(Object.keys(attributes));
  429. }
  430. [_getUnsetAttributes](protoAttributes) {
  431. const allAttr = this[_attributeNames];
  432. const setAttr = this[_setAttributes];
  433. return [...protoAttributes].filter(x => allAttr.has(x) && !setAttr.has(x));
  434. }
  435. [$resolvePrototypes](ids, ancestors = new Set()) {
  436. for (const child of this[_children]) {
  437. child[_resolvePrototypesHelper](ids, ancestors);
  438. }
  439. }
  440. [_resolvePrototypesHelper](ids, ancestors) {
  441. const proto = this[_getPrototype](ids, ancestors);
  442. if (proto) {
  443. this[_applyPrototype](proto, ids, ancestors);
  444. } else {
  445. this[$resolvePrototypes](ids, ancestors);
  446. }
  447. }
  448. [_getPrototype](ids, ancestors) {
  449. const {
  450. use,
  451. usehref
  452. } = this;
  453. if (!use && !usehref) {
  454. return null;
  455. }
  456. let proto = null;
  457. let somExpression = null;
  458. let id = null;
  459. let ref = use;
  460. if (usehref) {
  461. ref = usehref;
  462. if (usehref.startsWith("#som(") && usehref.endsWith(")")) {
  463. somExpression = usehref.slice("#som(".length, usehref.length - 1);
  464. } else if (usehref.startsWith(".#som(") && usehref.endsWith(")")) {
  465. somExpression = usehref.slice(".#som(".length, usehref.length - 1);
  466. } else if (usehref.startsWith("#")) {
  467. id = usehref.slice(1);
  468. } else if (usehref.startsWith(".#")) {
  469. id = usehref.slice(2);
  470. }
  471. } else if (use.startsWith("#")) {
  472. id = use.slice(1);
  473. } else {
  474. somExpression = use;
  475. }
  476. this.use = this.usehref = "";
  477. if (id) {
  478. proto = ids.get(id);
  479. } else {
  480. proto = (0, _som.searchNode)(ids.get($root), this, somExpression, true, false);
  481. if (proto) {
  482. proto = proto[0];
  483. }
  484. }
  485. if (!proto) {
  486. (0, _util.warn)(`XFA - Invalid prototype reference: ${ref}.`);
  487. return null;
  488. }
  489. if (proto[$nodeName] !== this[$nodeName]) {
  490. (0, _util.warn)(`XFA - Incompatible prototype: ${proto[$nodeName]} !== ${this[$nodeName]}.`);
  491. return null;
  492. }
  493. if (ancestors.has(proto)) {
  494. (0, _util.warn)(`XFA - Cycle detected in prototypes use.`);
  495. return null;
  496. }
  497. ancestors.add(proto);
  498. const protoProto = proto[_getPrototype](ids, ancestors);
  499. if (protoProto) {
  500. proto[_applyPrototype](protoProto, ids, ancestors);
  501. }
  502. proto[$resolvePrototypes](ids, ancestors);
  503. ancestors.delete(proto);
  504. return proto;
  505. }
  506. [_applyPrototype](proto, ids, ancestors) {
  507. if (ancestors.has(proto)) {
  508. (0, _util.warn)(`XFA - Cycle detected in prototypes use.`);
  509. return;
  510. }
  511. if (!this[$content] && proto[$content]) {
  512. this[$content] = proto[$content];
  513. }
  514. const newAncestors = new Set(ancestors);
  515. newAncestors.add(proto);
  516. for (const unsetAttrName of this[_getUnsetAttributes](proto[_setAttributes])) {
  517. this[unsetAttrName] = proto[unsetAttrName];
  518. if (this[_setAttributes]) {
  519. this[_setAttributes].add(unsetAttrName);
  520. }
  521. }
  522. for (const name of Object.getOwnPropertyNames(this)) {
  523. if (this[_attributeNames].has(name)) {
  524. continue;
  525. }
  526. const value = this[name];
  527. const protoValue = proto[name];
  528. if (value instanceof XFAObjectArray) {
  529. for (const child of value[_children]) {
  530. child[_resolvePrototypesHelper](ids, ancestors);
  531. }
  532. for (let i = value[_children].length, ii = protoValue[_children].length; i < ii; i++) {
  533. const child = proto[_children][i][$clone]();
  534. if (value.push(child)) {
  535. child[_parent] = this;
  536. this[_children].push(child);
  537. child[_resolvePrototypesHelper](ids, ancestors);
  538. } else {
  539. break;
  540. }
  541. }
  542. continue;
  543. }
  544. if (value !== null) {
  545. value[$resolvePrototypes](ids, ancestors);
  546. if (protoValue) {
  547. value[_applyPrototype](protoValue, ids, ancestors);
  548. }
  549. continue;
  550. }
  551. if (protoValue !== null) {
  552. const child = protoValue[$clone]();
  553. child[_parent] = this;
  554. this[name] = child;
  555. this[_children].push(child);
  556. child[_resolvePrototypesHelper](ids, ancestors);
  557. }
  558. }
  559. }
  560. static [_cloneAttribute](obj) {
  561. if (Array.isArray(obj)) {
  562. return obj.map(x => XFAObject[_cloneAttribute](x));
  563. }
  564. if (typeof obj === "object" && obj !== null) {
  565. return Object.assign({}, obj);
  566. }
  567. return obj;
  568. }
  569. [$clone]() {
  570. const clone = Object.create(Object.getPrototypeOf(this));
  571. for (const $symbol of Object.getOwnPropertySymbols(this)) {
  572. try {
  573. clone[$symbol] = this[$symbol];
  574. } catch (_) {
  575. (0, _util.shadow)(clone, $symbol, this[$symbol]);
  576. }
  577. }
  578. clone[$uid] = `${clone[$nodeName]}${uid++}`;
  579. clone[_children] = [];
  580. for (const name of Object.getOwnPropertyNames(this)) {
  581. if (this[_attributeNames].has(name)) {
  582. clone[name] = XFAObject[_cloneAttribute](this[name]);
  583. continue;
  584. }
  585. const value = this[name];
  586. if (value instanceof XFAObjectArray) {
  587. clone[name] = new XFAObjectArray(value[_max]);
  588. } else {
  589. clone[name] = null;
  590. }
  591. }
  592. for (const child of this[_children]) {
  593. const name = child[$nodeName];
  594. const clonedChild = child[$clone]();
  595. clone[_children].push(clonedChild);
  596. clonedChild[_parent] = clone;
  597. if (clone[name] === null) {
  598. clone[name] = clonedChild;
  599. } else {
  600. clone[name][_children].push(clonedChild);
  601. }
  602. }
  603. return clone;
  604. }
  605. [$getChildren](name = null) {
  606. if (!name) {
  607. return this[_children];
  608. }
  609. return this[_children].filter(c => c[$nodeName] === name);
  610. }
  611. [$getChildrenByClass](name) {
  612. return this[name];
  613. }
  614. [$getChildrenByName](name, allTransparent, first = true) {
  615. return Array.from(this[$getChildrenByNameIt](name, allTransparent, first));
  616. }
  617. *[$getChildrenByNameIt](name, allTransparent, first = true) {
  618. if (name === "parent") {
  619. yield this[_parent];
  620. return;
  621. }
  622. for (const child of this[_children]) {
  623. if (child[$nodeName] === name) {
  624. yield child;
  625. }
  626. if (child.name === name) {
  627. yield child;
  628. }
  629. if (allTransparent || child[$isTransparent]()) {
  630. yield* child[$getChildrenByNameIt](name, allTransparent, false);
  631. }
  632. }
  633. if (first && this[_attributeNames].has(name)) {
  634. yield new XFAAttribute(this, name, this[name]);
  635. }
  636. }
  637. }
  638. exports.XFAObject = XFAObject;
  639. class XFAObjectArray {
  640. constructor(max = Infinity) {
  641. this[_max] = max;
  642. this[_children] = [];
  643. }
  644. push(child) {
  645. const len = this[_children].length;
  646. if (len <= this[_max]) {
  647. this[_children].push(child);
  648. return true;
  649. }
  650. (0, _util.warn)(`XFA - node "${child[$nodeName]}" accepts no more than ${this[_max]} children`);
  651. return false;
  652. }
  653. isEmpty() {
  654. return this[_children].length === 0;
  655. }
  656. dump() {
  657. return this[_children].length === 1 ? this[_children][0][$dump]() : this[_children].map(x => x[$dump]());
  658. }
  659. [$clone]() {
  660. const clone = new XFAObjectArray(this[_max]);
  661. clone[_children] = this[_children].map(c => c[$clone]());
  662. return clone;
  663. }
  664. get children() {
  665. return this[_children];
  666. }
  667. clear() {
  668. this[_children].length = 0;
  669. }
  670. }
  671. exports.XFAObjectArray = XFAObjectArray;
  672. class XFAAttribute {
  673. constructor(node, name, value) {
  674. this[_parent] = node;
  675. this[$nodeName] = name;
  676. this[$content] = value;
  677. this[$consumed] = false;
  678. this[$uid] = `attribute${uid++}`;
  679. }
  680. [$getParent]() {
  681. return this[_parent];
  682. }
  683. [$isDataValue]() {
  684. return true;
  685. }
  686. [$getDataValue]() {
  687. return this[$content].trim();
  688. }
  689. [$setValue](value) {
  690. value = value.value || "";
  691. this[$content] = value.toString();
  692. }
  693. [$text]() {
  694. return this[$content];
  695. }
  696. [$isDescendent](parent) {
  697. return this[_parent] === parent || this[_parent][$isDescendent](parent);
  698. }
  699. }
  700. exports.XFAAttribute = XFAAttribute;
  701. class XmlObject extends XFAObject {
  702. constructor(nsId, name, attributes = {}) {
  703. super(nsId, name);
  704. this[$content] = "";
  705. this[_dataValue] = null;
  706. if (name !== "#text") {
  707. const map = new Map();
  708. this[_attributes] = map;
  709. for (const [attrName, value] of Object.entries(attributes)) {
  710. map.set(attrName, new XFAAttribute(this, attrName, value));
  711. }
  712. if (attributes.hasOwnProperty($nsAttributes)) {
  713. const dataNode = attributes[$nsAttributes].xfa.dataNode;
  714. if (dataNode !== undefined) {
  715. if (dataNode === "dataGroup") {
  716. this[_dataValue] = false;
  717. } else if (dataNode === "dataValue") {
  718. this[_dataValue] = true;
  719. }
  720. }
  721. }
  722. }
  723. this[$consumed] = false;
  724. }
  725. [$toString](buf) {
  726. const tagName = this[$nodeName];
  727. if (tagName === "#text") {
  728. buf.push((0, _core_utils.encodeToXmlString)(this[$content]));
  729. return;
  730. }
  731. const utf8TagName = (0, _util.utf8StringToString)(tagName);
  732. const prefix = this[$namespaceId] === NS_DATASETS ? "xfa:" : "";
  733. buf.push(`<${prefix}${utf8TagName}`);
  734. for (const [name, value] of this[_attributes].entries()) {
  735. const utf8Name = (0, _util.utf8StringToString)(name);
  736. buf.push(` ${utf8Name}="${(0, _core_utils.encodeToXmlString)(value[$content])}"`);
  737. }
  738. if (this[_dataValue] !== null) {
  739. if (this[_dataValue]) {
  740. buf.push(` xfa:dataNode="dataValue"`);
  741. } else {
  742. buf.push(` xfa:dataNode="dataGroup"`);
  743. }
  744. }
  745. if (!this[$content] && this[_children].length === 0) {
  746. buf.push("/>");
  747. return;
  748. }
  749. buf.push(">");
  750. if (this[$content]) {
  751. if (typeof this[$content] === "string") {
  752. buf.push((0, _core_utils.encodeToXmlString)(this[$content]));
  753. } else {
  754. this[$content][$toString](buf);
  755. }
  756. } else {
  757. for (const child of this[_children]) {
  758. child[$toString](buf);
  759. }
  760. }
  761. buf.push(`</${prefix}${utf8TagName}>`);
  762. }
  763. [$onChild](child) {
  764. if (this[$content]) {
  765. const node = new XmlObject(this[$namespaceId], "#text");
  766. this[$appendChild](node);
  767. node[$content] = this[$content];
  768. this[$content] = "";
  769. }
  770. this[$appendChild](child);
  771. return true;
  772. }
  773. [$onText](str) {
  774. this[$content] += str;
  775. }
  776. [$finalize]() {
  777. if (this[$content] && this[_children].length > 0) {
  778. const node = new XmlObject(this[$namespaceId], "#text");
  779. this[$appendChild](node);
  780. node[$content] = this[$content];
  781. delete this[$content];
  782. }
  783. }
  784. [$toHTML]() {
  785. if (this[$nodeName] === "#text") {
  786. return _utils.HTMLResult.success({
  787. name: "#text",
  788. value: this[$content]
  789. });
  790. }
  791. return _utils.HTMLResult.EMPTY;
  792. }
  793. [$getChildren](name = null) {
  794. if (!name) {
  795. return this[_children];
  796. }
  797. return this[_children].filter(c => c[$nodeName] === name);
  798. }
  799. [$getAttributes]() {
  800. return this[_attributes];
  801. }
  802. [$getChildrenByClass](name) {
  803. const value = this[_attributes].get(name);
  804. if (value !== undefined) {
  805. return value;
  806. }
  807. return this[$getChildren](name);
  808. }
  809. *[$getChildrenByNameIt](name, allTransparent) {
  810. const value = this[_attributes].get(name);
  811. if (value) {
  812. yield value;
  813. }
  814. for (const child of this[_children]) {
  815. if (child[$nodeName] === name) {
  816. yield child;
  817. }
  818. if (allTransparent) {
  819. yield* child[$getChildrenByNameIt](name, allTransparent);
  820. }
  821. }
  822. }
  823. *[$getAttributeIt](name, skipConsumed) {
  824. const value = this[_attributes].get(name);
  825. if (value && (!skipConsumed || !value[$consumed])) {
  826. yield value;
  827. }
  828. for (const child of this[_children]) {
  829. yield* child[$getAttributeIt](name, skipConsumed);
  830. }
  831. }
  832. *[$getRealChildrenByNameIt](name, allTransparent, skipConsumed) {
  833. for (const child of this[_children]) {
  834. if (child[$nodeName] === name && (!skipConsumed || !child[$consumed])) {
  835. yield child;
  836. }
  837. if (allTransparent) {
  838. yield* child[$getRealChildrenByNameIt](name, allTransparent, skipConsumed);
  839. }
  840. }
  841. }
  842. [$isDataValue]() {
  843. if (this[_dataValue] === null) {
  844. return this[_children].length === 0 || this[_children][0][$namespaceId] === _namespaces.NamespaceIds.xhtml.id;
  845. }
  846. return this[_dataValue];
  847. }
  848. [$getDataValue]() {
  849. if (this[_dataValue] === null) {
  850. if (this[_children].length === 0) {
  851. return this[$content].trim();
  852. }
  853. if (this[_children][0][$namespaceId] === _namespaces.NamespaceIds.xhtml.id) {
  854. return this[_children][0][$text]().trim();
  855. }
  856. return null;
  857. }
  858. return this[$content].trim();
  859. }
  860. [$setValue](value) {
  861. value = value.value || "";
  862. this[$content] = value.toString();
  863. }
  864. [$dump](hasNS = false) {
  865. const dumped = Object.create(null);
  866. if (hasNS) {
  867. dumped.$ns = this[$namespaceId];
  868. }
  869. if (this[$content]) {
  870. dumped.$content = this[$content];
  871. }
  872. dumped.$name = this[$nodeName];
  873. dumped.children = [];
  874. for (const child of this[_children]) {
  875. dumped.children.push(child[$dump](hasNS));
  876. }
  877. dumped.attributes = Object.create(null);
  878. for (const [name, value] of this[_attributes]) {
  879. dumped.attributes[name] = value[$content];
  880. }
  881. return dumped;
  882. }
  883. }
  884. exports.XmlObject = XmlObject;
  885. class ContentObject extends XFAObject {
  886. constructor(nsId, name) {
  887. super(nsId, name);
  888. this[$content] = "";
  889. }
  890. [$onText](text) {
  891. this[$content] += text;
  892. }
  893. [$finalize]() {}
  894. }
  895. exports.ContentObject = ContentObject;
  896. class OptionObject extends ContentObject {
  897. constructor(nsId, name, options) {
  898. super(nsId, name);
  899. this[_options] = options;
  900. }
  901. [$finalize]() {
  902. this[$content] = (0, _utils.getKeyword)({
  903. data: this[$content],
  904. defaultValue: this[_options][0],
  905. validate: k => this[_options].includes(k)
  906. });
  907. }
  908. [$clean](builder) {
  909. super[$clean](builder);
  910. delete this[_options];
  911. }
  912. }
  913. exports.OptionObject = OptionObject;
  914. class StringObject extends ContentObject {
  915. [$finalize]() {
  916. this[$content] = this[$content].trim();
  917. }
  918. }
  919. exports.StringObject = StringObject;
  920. class IntegerObject extends ContentObject {
  921. constructor(nsId, name, defaultValue, validator) {
  922. super(nsId, name);
  923. this[_defaultValue] = defaultValue;
  924. this[_validator] = validator;
  925. }
  926. [$finalize]() {
  927. this[$content] = (0, _utils.getInteger)({
  928. data: this[$content],
  929. defaultValue: this[_defaultValue],
  930. validate: this[_validator]
  931. });
  932. }
  933. [$clean](builder) {
  934. super[$clean](builder);
  935. delete this[_defaultValue];
  936. delete this[_validator];
  937. }
  938. }
  939. exports.IntegerObject = IntegerObject;
  940. class Option01 extends IntegerObject {
  941. constructor(nsId, name) {
  942. super(nsId, name, 0, n => n === 1);
  943. }
  944. }
  945. exports.Option01 = Option01;
  946. class Option10 extends IntegerObject {
  947. constructor(nsId, name) {
  948. super(nsId, name, 1, n => n === 0);
  949. }
  950. }
  951. exports.Option10 = Option10;