From cc8ac95addd692cd251df951b2606ef0cdbeaef1 Mon Sep 17 00:00:00 2001 From: Wojciech Maj Date: Fri, 19 Jan 2024 11:46:21 +0100 Subject: [PATCH] fix: fix 100s of (mostly) JSDoc issues found by TypeScript (#2514) --- packages/fns/src/asyncCompose.js | 10 +- packages/fns/src/capitalize.js | 8 +- packages/fns/src/castArray.js | 5 +- packages/fns/src/compose.js | 10 +- packages/fns/src/matchPercent.js | 12 ++- packages/fns/src/upperFirst.js | 6 +- packages/layout/src/canvas/measureCanvas.js | 19 ++-- packages/layout/src/image/getRatio.js | 6 +- packages/layout/src/image/getSource.js | 6 +- packages/layout/src/image/measureImage.js | 19 ++-- packages/layout/src/image/resolveSource.js | 2 +- packages/layout/src/node/createInstances.js | 12 +-- packages/layout/src/node/getBorderWidth.js | 4 +- packages/layout/src/node/getDimension.js | 4 +- packages/layout/src/node/getMargin.js | 4 +- packages/layout/src/node/getOrigin.js | 6 +- packages/layout/src/node/getPadding.js | 4 +- packages/layout/src/node/getPosition.js | 4 +- packages/layout/src/node/setAlign.js | 18 +++- packages/layout/src/node/setAlignContent.js | 4 +- packages/layout/src/node/setAlignItems.js | 4 +- packages/layout/src/node/setAlignSelf.js | 4 +- packages/layout/src/node/setAspectRatio.js | 11 +- packages/layout/src/node/setBorderWidth.js | 35 ++++--- packages/layout/src/node/setDimension.js | 24 ++--- packages/layout/src/node/setDisplay.js | 11 +- packages/layout/src/node/setFlexBasis.js | 4 +- packages/layout/src/node/setFlexDirection.js | 11 +- packages/layout/src/node/setFlexGrow.js | 11 +- packages/layout/src/node/setFlexShrink.js | 11 +- packages/layout/src/node/setFlexWrap.js | 11 +- packages/layout/src/node/setGap.js | 23 ++-- packages/layout/src/node/setJustifyContent.js | 11 +- packages/layout/src/node/setMargin.js | 35 ++++--- packages/layout/src/node/setOverflow.js | 11 +- packages/layout/src/node/setPadding.js | 35 ++++--- packages/layout/src/node/setPosition.js | 35 ++++--- packages/layout/src/node/setPositionType.js | 11 +- packages/layout/src/node/setYogaValue.js | 20 +++- packages/layout/src/page/getOrientation.js | 6 +- packages/layout/src/page/getSize.js | 41 ++++---- packages/layout/src/page/isHeightAuto.js | 2 +- packages/layout/src/page/isLandscape.js | 2 +- packages/layout/src/page/isPortrait.js | 2 +- packages/layout/src/steps/resolveAssets.js | 13 +-- .../layout/src/steps/resolveDimensions.js | 27 +++-- .../layout/src/steps/resolveInheritance.js | 13 ++- .../src/steps/resolveLinkSubstitution.js | 8 +- packages/layout/src/steps/resolveOrigins.js | 4 +- .../layout/src/steps/resolvePagePaddings.js | 34 +++--- packages/layout/src/steps/resolvePageSizes.js | 2 +- .../layout/src/steps/resolvePagination.js | 22 ++-- .../layout/src/steps/resolvePercentHeight.js | 14 +-- .../layout/src/steps/resolvePercentRadius.js | 15 ++- packages/layout/src/steps/resolveStyles.js | 15 ++- packages/layout/src/steps/resolveSvg.js | 2 +- packages/layout/src/svg/measureSvg.js | 49 ++++----- packages/layout/src/text/fromFragments.js | 8 +- .../layout/src/text/getAttributedString.js | 12 ++- packages/layout/src/text/heightAtLineIndex.js | 2 +- packages/layout/src/text/layoutText.js | 18 ++-- packages/layout/src/text/lineIndexAtHeight.js | 2 +- packages/layout/src/text/linesHeight.js | 4 +- packages/layout/src/text/linesWidth.js | 6 +- packages/layout/src/text/measureText.js | 15 ++- packages/layout/src/text/transformText.js | 6 +- packages/pdfkit/src/document.js | 29 ++++- packages/pdfkit/src/mixins/text.js | 9 +- packages/pdfkit/src/tree.js | 12 ++- packages/render/src/svg/parsePoints.js | 15 ++- packages/renderer/src/dom/usePDF.js | 6 ++ packages/renderer/src/node/renderTo.js | 13 +++ packages/renderer/src/utils/propsEqual.js | 6 +- .../renderer/tests/dynamicContent.test.jsx | 28 +++++ packages/renderer/tests/node.test.js | 3 + ...-content-should-render-an-image-1-snap.png | Bin 0 -> 20778 bytes packages/stylesheet/src/expand/boxModel.js | 6 ++ packages/stylesheet/src/expand/flex.js | 6 ++ packages/stylesheet/src/expand/index.js | 12 +-- packages/stylesheet/src/flatten/index.js | 17 +-- packages/stylesheet/src/transform/colors.js | 6 +- packages/stylesheet/src/transform/index.js | 12 ++- packages/stylesheet/src/transform/units.js | 6 +- packages/stylesheet/src/utils/castFloat.js | 6 +- packages/stylesheet/tests/resolve.test.js | 2 +- packages/svgkit/src/document/index.js | 14 ++- packages/svgkit/src/page/index.js | 11 +- packages/svgkit/src/utils/getPageSize.js | 42 ++++---- .../src/attributedString/advanceWidth.js | 8 +- .../attributedString/advanceWidthBetween.js | 8 +- .../textkit/src/attributedString/append.js | 4 +- .../textkit/src/attributedString/ascent.js | 8 +- .../textkit/src/attributedString/descent.js | 8 +- .../textkit/src/attributedString/dropLast.js | 12 +-- .../textkit/src/attributedString/empty.js | 2 +- packages/textkit/src/attributedString/end.js | 4 +- .../src/attributedString/fromFragments.js | 8 +- .../src/attributedString/glyphWidthAt.js | 6 +- .../textkit/src/attributedString/height.js | 8 +- .../src/attributedString/indexAtOffset.js | 6 +- .../src/attributedString/insertGlyph.js | 4 +- .../src/attributedString/leadingOffset.js | 4 +- .../textkit/src/attributedString/length.js | 4 +- .../textkit/src/attributedString/prepend.js | 4 +- .../textkit/src/attributedString/runAt.js | 6 +- .../src/attributedString/runIndexAt.js | 6 +- .../textkit/src/attributedString/slice.js | 20 ++-- .../src/attributedString/sliceAtOffset.js | 6 +- .../textkit/src/attributedString/start.js | 4 +- .../src/attributedString/trailingOffset.js | 4 +- packages/textkit/src/attributedString/trim.js | 4 +- packages/textkit/src/block/height.js | 4 +- packages/textkit/src/block/sliceAtHeight.js | 6 +- packages/textkit/src/block/truncate.js | 9 +- .../src/engines/fontSubstitution/index.js | 10 +- .../src/engines/justification/index.js | 17 +-- .../textkit/src/engines/linebreaker/index.js | 34 +++--- .../src/engines/linebreaker/linebreak.js | 6 ++ .../src/engines/linebreaker/linkedList.js | 1 + .../src/engines/scriptItemizer/index.js | 10 +- packages/textkit/src/glyph/fromCodePoint.js | 6 +- packages/textkit/src/glyph/isWhiteSpace.js | 6 +- packages/textkit/src/glyph/slice.js | 10 +- packages/textkit/src/indices/append.js | 6 +- packages/textkit/src/indices/normalize.js | 4 +- packages/textkit/src/indices/prepend.js | 8 +- packages/textkit/src/indices/resolve.js | 8 +- .../textkit/src/layout/applyDefaultStyles.js | 19 ++-- .../textkit/src/layout/finalizeFragments.js | 99 ++++++++++-------- packages/textkit/src/layout/generateGlyphs.js | 34 +++--- packages/textkit/src/layout/index.js | 27 +++-- .../textkit/src/layout/layoutParagraph.js | 32 +++--- packages/textkit/src/layout/preprocessRuns.js | 13 ++- .../textkit/src/layout/resolveAttachments.js | 15 +-- packages/textkit/src/layout/resolveYOffset.js | 15 +-- .../textkit/src/layout/splitParagraphs.js | 13 ++- packages/textkit/src/layout/typesetter.js | 17 +-- packages/textkit/src/layout/verticalAlign.js | 10 +- packages/textkit/src/layout/wrapWords.js | 77 +++++++------- .../textkit/src/positions/advanceWidth.js | 4 +- packages/textkit/src/rect/area.js | 4 +- packages/textkit/src/rect/bottomLeft.js | 4 +- packages/textkit/src/rect/bottomRight.js | 4 +- packages/textkit/src/rect/copy.js | 4 +- packages/textkit/src/rect/crop.js | 4 +- packages/textkit/src/rect/empty.js | 2 +- packages/textkit/src/rect/equals.js | 6 +- packages/textkit/src/rect/intersects.js | 10 +- packages/textkit/src/rect/maxX.js | 4 +- packages/textkit/src/rect/maxY.js | 4 +- packages/textkit/src/run/add.js | 6 +- packages/textkit/src/run/advanceWidth.js | 4 +- .../textkit/src/run/advanceWidthBetween.js | 8 +- packages/textkit/src/run/append.js | 12 +-- packages/textkit/src/run/ascent.js | 4 +- packages/textkit/src/run/concat.js | 6 +- packages/textkit/src/run/descent.js | 4 +- packages/textkit/src/run/dropLast.js | 4 +- packages/textkit/src/run/empty.js | 2 +- packages/textkit/src/run/filter.js | 8 +- packages/textkit/src/run/flatten.js | 18 ++-- packages/textkit/src/run/getFont.js | 4 +- packages/textkit/src/run/glyphIndexAt.js | 6 +- packages/textkit/src/run/height.js | 4 +- packages/textkit/src/run/indexAtOffset.js | 6 +- packages/textkit/src/run/insert.js | 16 +-- packages/textkit/src/run/isEmpty.js | 4 +- packages/textkit/src/run/leadingOffset.js | 14 +-- packages/textkit/src/run/length.js | 4 +- packages/textkit/src/run/lineGap.js | 4 +- packages/textkit/src/run/offset.js | 6 +- packages/textkit/src/run/omit.js | 4 +- packages/textkit/src/run/prepend.js | 12 +-- packages/textkit/src/run/runIndexAt.js | 8 +- packages/textkit/src/run/scale.js | 8 +- packages/textkit/src/run/slice.js | 8 +- packages/textkit/src/run/sort.js | 7 +- packages/textkit/src/run/subtract.js | 6 +- packages/textkit/src/run/trailingOffset.js | 21 ++-- .../textkit/src/utils/stringFromCodePoints.js | 4 +- .../tests/engines/fontSubstitution.test.js | 2 +- .../tests/engines/scriptItemizer.test.js | 2 +- .../tests/engines/wordHyphenation.test.js | 2 +- .../tests/internal/fontSubstitutionEngine.js | 4 +- .../textkit/tests/internal/scriptItemizer.js | 4 +- .../textkit/tests/run/indexAtOffset.test.js | 4 +- 186 files changed, 1233 insertions(+), 807 deletions(-) create mode 100644 packages/renderer/tests/dynamicContent.test.jsx create mode 100644 packages/renderer/tests/snapshots/dynamic-content-test-jsx-tests-dynamic-content-test-jsx-dynamic-content-should-render-an-image-1-snap.png diff --git a/packages/fns/src/asyncCompose.js b/packages/fns/src/asyncCompose.js index d87131239..2b9b259bb 100644 --- a/packages/fns/src/asyncCompose.js +++ b/packages/fns/src/asyncCompose.js @@ -2,10 +2,18 @@ import reverse from './reverse'; +/** + * @typedef {Function} AsyncCompose + * @param {any} value + * @param {...any} args + * @returns {any} result + */ + /** * Performs right-to-left function composition with async functions support * - * @param {...any} functions + * @param {...Function} fns functions + * @returns {AsyncCompose} composed function */ const asyncCompose = (...fns) => async (value, ...args) => { let result = value; diff --git a/packages/fns/src/capitalize.js b/packages/fns/src/capitalize.js index b9b80275b..f440bb248 100644 --- a/packages/fns/src/capitalize.js +++ b/packages/fns/src/capitalize.js @@ -1,12 +1,12 @@ /** * Capitalize first letter of each word * - * @param {String} string - * @returns {String} capitalized string + * @param {string} value string + * @returns {string} capitalized string */ -const capitalize = value => { +const capitalize = (value) => { if (!value) return value; - return value.replace(/(^|\s)\S/g, l => l.toUpperCase()); + return value.replace(/(^|\s)\S/g, (l) => l.toUpperCase()); }; export default capitalize; diff --git a/packages/fns/src/castArray.js b/packages/fns/src/castArray.js index 457126e33..720863985 100644 --- a/packages/fns/src/castArray.js +++ b/packages/fns/src/castArray.js @@ -1,8 +1,9 @@ /** * Casts value to array * - * @param {any} value - * @returns {Array} casted value + * @template T + * @param {T|T[]} value value + * @returns {T[]} array */ const castArray = value => { return Array.isArray(value) ? value : [value]; diff --git a/packages/fns/src/compose.js b/packages/fns/src/compose.js index 242957349..cad85e6d7 100644 --- a/packages/fns/src/compose.js +++ b/packages/fns/src/compose.js @@ -2,10 +2,18 @@ import reverse from './reverse'; +/** + * @typedef {Function} Compose + * @param {any} value + * @param {...any} args + * @returns {any} result + */ + /** * Performs right-to-left function composition * - * @param {...any} functions + * @param {...Function} fns functions + * @returns {Compose} composed function */ const compose = (...fns) => (value, ...args) => { let result = value; diff --git a/packages/fns/src/matchPercent.js b/packages/fns/src/matchPercent.js index 23f8913e7..b49c70054 100644 --- a/packages/fns/src/matchPercent.js +++ b/packages/fns/src/matchPercent.js @@ -1,16 +1,20 @@ -const isPercent = value => /((-)?\d+\.?\d*)%/g.exec(value); +/** + * @param {string | number} value + * @returns {RegExpExecArray | null} match + */ +const isPercent = value => /((-)?\d+\.?\d*)%/g.exec(`${value}`); /** * Get percentage value of input * - * @param {String} value - * @returns {Object} percent value (if matches) + * @param {string | number} value + * @returns {{ percent: number, value: number } | null} percent value (if matches) */ const matchPercent = value => { const match = isPercent(value); if (match) { - const f = parseFloat(match[1], 10); + const f = parseFloat(match[1]); const percent = f / 100; return { percent, value: f }; diff --git a/packages/fns/src/upperFirst.js b/packages/fns/src/upperFirst.js index 04a01d443..43fc775cc 100644 --- a/packages/fns/src/upperFirst.js +++ b/packages/fns/src/upperFirst.js @@ -1,10 +1,10 @@ /** * Capitalize first letter of string * - * @param {String} string - * @returns {String} capitalized string + * @param {string} value string + * @returns {string} capitalized string */ -const upperFirst = value => { +const upperFirst = (value) => { if (!value) return value; return value.charAt(0).toUpperCase() + value.slice(1); }; diff --git a/packages/layout/src/canvas/measureCanvas.js b/packages/layout/src/canvas/measureCanvas.js index 8a1828f80..a6a3ab500 100644 --- a/packages/layout/src/canvas/measureCanvas.js +++ b/packages/layout/src/canvas/measureCanvas.js @@ -6,7 +6,7 @@ import isHeightAuto from '../page/isHeightAuto'; const SAFETY_HEIGHT = 10; -const getMax = values => Math.max(-Infinity, ...values); +const getMax = (values) => Math.max(-Infinity, ...values); /** * Helper object to predict canvas size @@ -88,22 +88,23 @@ const measureCtx = () => { ctx.linearGradient = nil; ctx.radialGradient = nil; - ctx.getWidth = () => getMax(points.map(p => p[0])); - ctx.getHeight = () => getMax(points.map(p => p[1])); + ctx.getWidth = () => getMax(points.map((p) => p[0])); + ctx.getHeight = () => getMax(points.map((p) => p[1])); return ctx; }; +/** + * @typedef {Function} MeasureCanvas + * @returns {{ width: number, height: number }} canvas width and height + */ + /** * Yoga canvas measure function * * @param {Object} page * @param {Object} node - * @param {Number} width - * @param {Number} widthMode - * @param {Number} height - * @param {Number} heightMode - * @returns {Object} canvas width and height + * @returns {MeasureCanvas} measure canvas */ const measureCanvas = (page, node) => () => { const imageMargin = getMargin(node); @@ -124,7 +125,7 @@ const measureCanvas = (page, node) => () => { const width = ctx.getWidth(); const height = Math.min(pageArea, ctx.getHeight()); - return { height, width }; + return { width, height }; }; export default measureCanvas; diff --git a/packages/layout/src/image/getRatio.js b/packages/layout/src/image/getRatio.js index 8178db7af..f395f7602 100644 --- a/packages/layout/src/image/getRatio.js +++ b/packages/layout/src/image/getRatio.js @@ -1,10 +1,10 @@ /** * Get image ratio * - * @param {Object} image node - * @returns {Number} image ratio + * @param {Object} node image node + * @returns {number} image ratio */ -const getRatio = node => { +const getRatio = (node) => { return node.image?.data ? node.image.width / node.image.height : 1; }; diff --git a/packages/layout/src/image/getSource.js b/packages/layout/src/image/getSource.js index 0618cba28..6e59f1f8d 100644 --- a/packages/layout/src/image/getSource.js +++ b/packages/layout/src/image/getSource.js @@ -1,10 +1,10 @@ /** * Get image source * - * @param {Object} image node - * @returns {String | Object} image src + * @param {Object} node image node + * @returns {string | Object} image src */ -const getSource = node => +const getSource = (node) => node.props?.src || node.props?.source || node.props?.href; export default getSource; diff --git a/packages/layout/src/image/measureImage.js b/packages/layout/src/image/measureImage.js index f1e0e3267..9fc70af0c 100644 --- a/packages/layout/src/image/measureImage.js +++ b/packages/layout/src/image/measureImage.js @@ -7,16 +7,21 @@ import isHeightAuto from '../page/isHeightAuto'; const SAFETY_HEIGHT = 10; +/** + * @typedef {Function} MeasureImage + * @param {number} width + * @param {number} widthMode + * @param {number} height + * @param {number} heightMode + * @returns {{ width: number, height: number }} image width and height + */ + /** * Yoga image measure function * - * @param {Object} page - * @param {Object} node - * @param {Number} width - * @param {Number} widthMode - * @param {Number} height - * @param {Number} heightMode - * @returns {Object} image width and height + * @param {Object} page page + * @param {Object} node node + * @returns {MeasureImage} measure image */ const measureImage = (page, node) => (width, widthMode, height, heightMode) => { const imageRatio = getRatio(node); diff --git a/packages/layout/src/image/resolveSource.js b/packages/layout/src/image/resolveSource.js index f8859bcbf..45ab9b18f 100644 --- a/packages/layout/src/image/resolveSource.js +++ b/packages/layout/src/image/resolveSource.js @@ -4,7 +4,7 @@ * Also it handles factories and async sources. * * @param {string | Object | Function} src - * @returns {object} resolved src + * @returns {Promise} resolved src */ const resolveSource = async src => { const source = typeof src === 'function' ? await src() : await src; diff --git a/packages/layout/src/node/createInstances.js b/packages/layout/src/node/createInstances.js index c221ad379..192608476 100644 --- a/packages/layout/src/node/createInstances.js +++ b/packages/layout/src/node/createInstances.js @@ -1,11 +1,11 @@ import { castArray } from '@react-pdf/fns'; import { TextInstance } from '@react-pdf/primitives'; -const isString = value => typeof value === 'string'; +const isString = (value) => typeof value === 'string'; -const isNumber = value => typeof value === 'number'; +const isNumber = (value) => typeof value === 'number'; -const isFragment = value => +const isFragment = (value) => value && value.type === Symbol.for('react.fragment'); /** @@ -13,10 +13,10 @@ const isFragment = value => * * Can return multiple instances in the case of arrays or fragments. * - * @param {Object} React element - * @returns {Array} parsed react elements + * @param {Object} element React element + * @returns {Object[]} parsed React elements */ -const createInstances = element => { +const createInstances = (element) => { if (!element) return []; if (isString(element) || isNumber(element)) { diff --git a/packages/layout/src/node/getBorderWidth.js b/packages/layout/src/node/getBorderWidth.js index 0801389f4..e4449d401 100644 --- a/packages/layout/src/node/getBorderWidth.js +++ b/packages/layout/src/node/getBorderWidth.js @@ -7,9 +7,9 @@ const getComputedBorder = (yogaNode, edge) => * Get Yoga computed border width. Zero otherwise * * @param {Object} node - * @return {Object} border widths + * @returns {{ borderTopWidth: number, borderRightWidth: number, borderBottomWidth: number, borderLeftWidth: number }} border widths */ -const getBorderWidth = node => { +const getBorderWidth = (node) => { const { yogaNode } = node; return { diff --git a/packages/layout/src/node/getDimension.js b/packages/layout/src/node/getDimension.js index e8f1e433e..d1228abd3 100644 --- a/packages/layout/src/node/getDimension.js +++ b/packages/layout/src/node/getDimension.js @@ -7,9 +7,9 @@ const DEFAULT_DIMENSION = { * Get Yoga computed dimensions. Zero otherwise * * @param {Object} node - * @return {Object} dimensions + * @returns {{ width: number, height: number }} dimensions */ -const getDimension = node => { +const getDimension = (node) => { const { yogaNode } = node; if (!yogaNode) return DEFAULT_DIMENSION; diff --git a/packages/layout/src/node/getMargin.js b/packages/layout/src/node/getMargin.js index bb45ff8fc..68742bb77 100644 --- a/packages/layout/src/node/getMargin.js +++ b/packages/layout/src/node/getMargin.js @@ -9,9 +9,9 @@ const getComputedMargin = (node, edge) => { * Get Yoga computed magins. Zero otherwise * * @param {Object} node - * @return {Object} margins + * @returns {{ marginTop: number, marginRight: number, marginBottom: number, marginLeft: number }} margins */ -const getMargin = node => { +const getMargin = (node) => { const { style, box } = node; const marginTop = diff --git a/packages/layout/src/node/getOrigin.js b/packages/layout/src/node/getOrigin.js index d7fed8b01..8a2ba3989 100644 --- a/packages/layout/src/node/getOrigin.js +++ b/packages/layout/src/node/getOrigin.js @@ -1,15 +1,15 @@ import { isNil, matchPercent } from '@react-pdf/fns'; -const getTransformStyle = s => node => +const getTransformStyle = (s) => (node) => isNil(node.style?.[s]) ? '50%' : node.style?.[s]; /** * Get node origin * * @param {Object} node - * @returns {Object} node origin + * @returns {{ left?: number, top?: number }} node origin */ -const getOrigin = node => { +const getOrigin = (node) => { if (!node.box) return {}; const { left, top, width, height } = node.box; diff --git a/packages/layout/src/node/getPadding.js b/packages/layout/src/node/getPadding.js index 70e5afe52..ac76c5a9c 100644 --- a/packages/layout/src/node/getPadding.js +++ b/packages/layout/src/node/getPadding.js @@ -9,9 +9,9 @@ const getComputedPadding = (node, edge) => { * Get Yoga computed paddings. Zero otherwise * * @param {Object} node - * @return {Object} paddings + * @returns {{ paddingTop: number, paddingRight: number, paddingBottom: number, paddingLeft: number }} paddings */ -const getPadding = node => { +const getPadding = (node) => { const { style, box } = node; const paddingTop = diff --git a/packages/layout/src/node/getPosition.js b/packages/layout/src/node/getPosition.js index 92e60f85a..c5cc0f7e5 100644 --- a/packages/layout/src/node/getPosition.js +++ b/packages/layout/src/node/getPosition.js @@ -2,9 +2,9 @@ * Get Yoga computed position. Zero otherwise * * @param {Object} node - * @return {Object} position + * @returns {{ top: number, right: number, bottom: number, left: number }} position */ -const getPosition = node => { +const getPosition = (node) => { const { yogaNode } = node; return { diff --git a/packages/layout/src/node/setAlign.js b/packages/layout/src/node/setAlign.js index 7e3edf527..9456c1dfb 100644 --- a/packages/layout/src/node/setAlign.js +++ b/packages/layout/src/node/setAlign.js @@ -11,13 +11,23 @@ const ALIGN = { 'space-around': Yoga.ALIGN_SPACE_AROUND, }; +/** + * @typedef {Function} NodeInstanceWrapper + * @param {Object} node node instance + * @returns {Object} node instance + */ + +/** + * @typedef {Function} AlignSetter + * @param {string} value align value + * @returns {NodeInstanceWrapper} node instance wrapper + */ + /** * Set generic align attribute to node's Yoga instance * - * @param {String} specific align property - * @param {String} align value - * @param {Object} node instance - * @return {Object} node instance + * @param {string} attr specific align property + * @returns {AlignSetter} align setter */ const setAlign = attr => value => node => { const { yogaNode } = node; diff --git a/packages/layout/src/node/setAlignContent.js b/packages/layout/src/node/setAlignContent.js index 96f446d4e..1bba23e09 100644 --- a/packages/layout/src/node/setAlignContent.js +++ b/packages/layout/src/node/setAlignContent.js @@ -3,9 +3,9 @@ import setAlign from './setAlign'; /** * Set align content attribute to node's Yoga instance * - * @param {String} align value + * @param {string} align value * @param {Object} node instance - * @return {Object} node instance + * @returns {Object} node instance */ const setAlignContent = setAlign('content'); diff --git a/packages/layout/src/node/setAlignItems.js b/packages/layout/src/node/setAlignItems.js index b2ede1307..239409524 100644 --- a/packages/layout/src/node/setAlignItems.js +++ b/packages/layout/src/node/setAlignItems.js @@ -3,9 +3,9 @@ import setAlign from './setAlign'; /** * Set align items attribute to node's Yoga instance * - * @param {String} align value + * @param {string} align value * @param {Object} node instance - * @return {Object} node instance + * @returns {Object} node instance */ const setAlignItems = setAlign('items'); diff --git a/packages/layout/src/node/setAlignSelf.js b/packages/layout/src/node/setAlignSelf.js index 8138d5cb4..7aba87f63 100644 --- a/packages/layout/src/node/setAlignSelf.js +++ b/packages/layout/src/node/setAlignSelf.js @@ -3,9 +3,9 @@ import setAlign from './setAlign'; /** * Set align self attribute to node's Yoga instance * - * @param {String} align value + * @param {string} align value * @param {Object} node instance - * @return {Object} node instance + * @returns {Object} node instance */ const setAlignSelf = setAlign('self'); diff --git a/packages/layout/src/node/setAspectRatio.js b/packages/layout/src/node/setAspectRatio.js index 18ec5d591..52b6eab20 100644 --- a/packages/layout/src/node/setAspectRatio.js +++ b/packages/layout/src/node/setAspectRatio.js @@ -1,11 +1,16 @@ import { isNil } from '@react-pdf/fns'; +/** + * @typedef {Function} NodeInstanceWrapper + * @param {Object} node node instance + * @returns {Object} node instance + */ + /** * Set aspect ratio attribute to node's Yoga instance * - * @param {Number} ratio - * @param {Object} node instance - * @return {Object} node instance + * @param {number} value ratio + * @returns {NodeInstanceWrapper} node instance wrapper */ const setAspectRatio = value => node => { const { yogaNode } = node; diff --git a/packages/layout/src/node/setBorderWidth.js b/packages/layout/src/node/setBorderWidth.js index 58b3bcf66..3eacd6af3 100644 --- a/packages/layout/src/node/setBorderWidth.js +++ b/packages/layout/src/node/setBorderWidth.js @@ -2,48 +2,53 @@ import Yoga from '../../yoga'; import setYogaValue from './setYogaValue'; +/** + * @typedef {Function} NodeInstanceWrapper + * @param {Object} node node instance + * @returns {Object} node instance + */ + /** * Set border top attribute to node's Yoga instance * - * @param {Number} border top width - * @param {Object} node instance - * @return {Object} node instance + * @param {number} border border top width + * @param {Object} node node instance + * @returns {Object} node instance */ export const setBorderTop = setYogaValue('border', Yoga.EDGE_TOP); /** * Set border right attribute to node's Yoga instance * - * @param {Number} border right width - * @param {Object} node instance - * @return {Object} node instance + * @param {number} border border right width + * @param {Object} node node instance + * @returns {Object} node instance */ export const setBorderRight = setYogaValue('border', Yoga.EDGE_RIGHT); /** * Set border bottom attribute to node's Yoga instance * - * @param {Number} border bottom width - * @param {Object} node instance - * @return {Object} node instance + * @param {number} border border bottom width + * @param {Object} node node instance + * @returns {Object} node instance */ export const setBorderBottom = setYogaValue('border', Yoga.EDGE_BOTTOM); /** * Set border left attribute to node's Yoga instance * - * @param {Number} border left width - * @param {Object} node instance - * @return {Object} node instance + * @param {number} border border left width + * @param {Object} node node instance + * @returns {Object} node instance */ export const setBorderLeft = setYogaValue('border', Yoga.EDGE_LEFT); /** * Set all border widths at once * - * @param {Number} border width - * @param {Object} node instance - * @return {Object} node instance + * @param {number | string} width border width + * @returns {NodeInstanceWrapper} node instance wrapper */ export const setBorder = width => node => { setBorderTop(width)(node); diff --git a/packages/layout/src/node/setDimension.js b/packages/layout/src/node/setDimension.js index 5b3e962ff..bb8c8b207 100644 --- a/packages/layout/src/node/setDimension.js +++ b/packages/layout/src/node/setDimension.js @@ -3,53 +3,53 @@ import setYogaValue from './setYogaValue'; /** * Set width to node's Yoga instance * - * @param {Number} width + * @param {number} width * @param {Object} node instance - * @return {Object} node instance + * @returns {Object} node instance */ export const setWidth = setYogaValue('width'); /** * Set min width to node's Yoga instance * - * @param {Number} min width + * @param {number} min width * @param {Object} node instance - * @return {Object} node instance + * @returns {Object} node instance */ export const setMinWidth = setYogaValue('minWidth'); /** * Set max width to node's Yoga instance * - * @param {Number} max width + * @param {number} max width * @param {Object} node instance - * @return {Object} node instance + * @returns {Object} node instance */ export const setMaxWidth = setYogaValue('maxWidth'); /** * Set height to node's Yoga instance * - * @param {Number} height + * @param {number} height * @param {Object} node instance - * @return {Object} node instance + * @returns {Object} node instance */ export const setHeight = setYogaValue('height'); /** * Set min height to node's Yoga instance * - * @param {Number} min height + * @param {number} min height * @param {Object} node instance - * @return {Object} node instance + * @returns {Object} node instance */ export const setMinHeight = setYogaValue('minHeight'); /** * Set max height to node's Yoga instance * - * @param {Number} max height + * @param {number} max height * @param {Object} node instance - * @return {Object} node instance + * @returns {Object} node instance */ export const setMaxHeight = setYogaValue('maxHeight'); diff --git a/packages/layout/src/node/setDisplay.js b/packages/layout/src/node/setDisplay.js index bf06ab00f..e8c9b5252 100644 --- a/packages/layout/src/node/setDisplay.js +++ b/packages/layout/src/node/setDisplay.js @@ -1,11 +1,16 @@ import Yoga from '../../yoga'; +/** + * @typedef {Function} NodeInstanceWrapper + * @param {Object} node node instance + * @returns {Object} node instance + */ + /** * Set display attribute to node's Yoga instance * - * @param {String} display - * @param {Object} node instance - * @return {Object} node instance + * @param {string} value display + * @returns {NodeInstanceWrapper} node instance wrapper */ const setDisplay = value => node => { const { yogaNode } = node; diff --git a/packages/layout/src/node/setFlexBasis.js b/packages/layout/src/node/setFlexBasis.js index b273c351e..e26958ce7 100644 --- a/packages/layout/src/node/setFlexBasis.js +++ b/packages/layout/src/node/setFlexBasis.js @@ -3,9 +3,9 @@ import setYogaValue from './setYogaValue'; /** * Set flex basis attribute to node's Yoga instance * - * @param {Number} flex basis value + * @param {number} flex basis value * @param {Object} node instance - * @return {Object} node instance + * @returns {Object} node instance */ const setFlexBasis = setYogaValue('flexBasis'); diff --git a/packages/layout/src/node/setFlexDirection.js b/packages/layout/src/node/setFlexDirection.js index 85cc2a77a..e55f30dd9 100644 --- a/packages/layout/src/node/setFlexDirection.js +++ b/packages/layout/src/node/setFlexDirection.js @@ -6,12 +6,17 @@ const FLEX_DIRECTIONS = { 'column-reverse': Yoga.FLEX_DIRECTION_COLUMN_REVERSE, }; +/** + * @typedef {Function} NodeInstanceWrapper + * @param {Object} node node instance + * @returns {Object} node instance + */ + /** * Set flex direction attribute to node's Yoga instance * - * @param {String} flex direction value - * @param {Object} node instance - * @return {Object} node instance + * @param {string} value flex direction value + * @returns {NodeInstanceWrapper} node instance wrapper */ const setFlexDirection = value => node => { const { yogaNode } = node; diff --git a/packages/layout/src/node/setFlexGrow.js b/packages/layout/src/node/setFlexGrow.js index 87aa1fc6b..d352fe600 100644 --- a/packages/layout/src/node/setFlexGrow.js +++ b/packages/layout/src/node/setFlexGrow.js @@ -1,11 +1,16 @@ import setYogaValue from './setYogaValue'; +/** + * @typedef {Function} NodeInstanceWrapper + * @param {Object} node node instance + * @returns {Object} node instance + */ + /** * Set flex grow attribute to node's Yoga instance * - * @param {Number} flex grow value - * @param {Object} node instance - * @return {Object} node instance + * @param {number} value flex grow value + * @returns {NodeInstanceWrapper} node instance wrapper */ const setFlexGrow = value => node => { return setYogaValue('flexGrow')(value || 0)(node); diff --git a/packages/layout/src/node/setFlexShrink.js b/packages/layout/src/node/setFlexShrink.js index af3d22eed..45ae764ea 100644 --- a/packages/layout/src/node/setFlexShrink.js +++ b/packages/layout/src/node/setFlexShrink.js @@ -1,11 +1,16 @@ import setYogaValue from './setYogaValue'; +/** + * @typedef {Function} NodeInstanceWrapper + * @param {Object} node node instance + * @returns {Object} node instance + */ + /** * Set flex shrink attribute to node's Yoga instance * - * @param {Number} flex shrink value - * @param {Object} node instance - * @return {Object} node instance + * @param {number} value flex shrink value + * @returns {NodeInstanceWrapper} node instance wrapper */ const setFlexShrink = value => node => { return setYogaValue('flexShrink')(value || 1)(node); diff --git a/packages/layout/src/node/setFlexWrap.js b/packages/layout/src/node/setFlexWrap.js index f7ad6e1b0..3c3baea0c 100644 --- a/packages/layout/src/node/setFlexWrap.js +++ b/packages/layout/src/node/setFlexWrap.js @@ -5,12 +5,17 @@ const FLEX_WRAP = { 'wrap-reverse': Yoga.WRAP_WRAP_REVERSE, }; +/** + * @typedef {Function} NodeInstanceWrapper + * @param {Object} node node instance + * @returns {Object} node instance + */ + /** * Set flex wrap attribute to node's Yoga instance * - * @param {String} flex wrap value - * @param {Object} node instance - * @return {Object} node instance + * @param {string} value flex wrap value + * @returns {NodeInstanceWrapper} node instance wrapper */ const setFlexWrap = value => node => { const { yogaNode } = node; diff --git a/packages/layout/src/node/setGap.js b/packages/layout/src/node/setGap.js index f327dd464..872f60dea 100644 --- a/packages/layout/src/node/setGap.js +++ b/packages/layout/src/node/setGap.js @@ -1,6 +1,19 @@ import { isNil, matchPercent } from '@react-pdf/fns'; import Yoga from '../../yoga'; +/** + * @typedef {Function} NodeInstanceWrapper + * @param {Object} node node instance + * @returns {Object} node instance + */ + +/** + * Check if value is a percentage and throw error if so + * + * @param {string} attr property + * @param {unknown} value + * @returns {void} + */ const checkPercents = (attr, value) => { const percent = matchPercent(value); @@ -12,9 +25,8 @@ const checkPercents = (attr, value) => { /** * Set rowGap value to node's Yoga instance * - * @param {Number} gap value - * @param {Object} node instance - * @return {Object} node instance + * @param {number} value gap value + * @returns {NodeInstanceWrapper} node instance wrapper */ export const setRowGap = value => node => { const { yogaNode } = node; @@ -30,9 +42,8 @@ export const setRowGap = value => node => { /** * Set columnGap value to node's Yoga instance * - * @param {Number} gap value - * @param {Object} node instance - * @return {Object} node instance + * @param {number} value gap value + * @returns {NodeInstanceWrapper} node instance wrapper */ export const setColumnGap = value => node => { const { yogaNode } = node; diff --git a/packages/layout/src/node/setJustifyContent.js b/packages/layout/src/node/setJustifyContent.js index 509f80fd9..21e2957ce 100644 --- a/packages/layout/src/node/setJustifyContent.js +++ b/packages/layout/src/node/setJustifyContent.js @@ -9,12 +9,17 @@ const JUSTIFY_CONTENT = { 'space-evenly': Yoga.JUSTIFY_SPACE_EVENLY, }; +/** + * @typedef {Function} NodeInstanceWrapper + * @param {Object} node node instance + * @returns {Object} node instance + */ + /** * Set justify content attribute to node's Yoga instance * - * @param {String} justify content value - * @param {Object} node instance - * @return {Object} node instance + * @param {string} value justify content value + * @returns {NodeInstanceWrapper} node instance wrapper */ const setJustifyContent = value => node => { const { yogaNode } = node; diff --git a/packages/layout/src/node/setMargin.js b/packages/layout/src/node/setMargin.js index 4c81a42ea..85a933ab3 100644 --- a/packages/layout/src/node/setMargin.js +++ b/packages/layout/src/node/setMargin.js @@ -2,48 +2,53 @@ import Yoga from '../../yoga'; import setYogaValue from './setYogaValue'; +/** + * @typedef {Function} NodeInstanceWrapper + * @param {Object} node node instance + * @returns {Object} node instance + */ + /** * Set margin top attribute to node's Yoga instance * - * @param {Number} margin top - * @param {Object} node instance - * @return {Object} node instance + * @param {number} margin margin top + * @param {Object} node node instance + * @returns {Object} node instance */ export const setMarginTop = setYogaValue('margin', Yoga.EDGE_TOP); /** * Set margin right attribute to node's Yoga instance * - * @param {Number} margin right - * @param {Object} node instance - * @return {Object} node instance + * @param {number} margin margin right + * @param {Object} node node instance + * @returns {Object} node instance */ export const setMarginRight = setYogaValue('margin', Yoga.EDGE_RIGHT); /** * Set margin bottom attribute to node's Yoga instance * - * @param {Number} margin bottom - * @param {Object} node instance - * @return {Object} node instance + * @param {number} margin margin bottom + * @param {Object} node node instance + * @returns {Object} node instance */ export const setMarginBottom = setYogaValue('margin', Yoga.EDGE_BOTTOM); /** * Set margin left attribute to node's Yoga instance * - * @param {Number} margin left - * @param {Object} node instance - * @return {Object} node instance + * @param {number} margin margin left + * @param {Object} node node instance + * @returns {Object} node instance */ export const setMarginLeft = setYogaValue('margin', Yoga.EDGE_LEFT); /** * Set all margins at once * - * @param {Number} margin - * @param {Object} node instance - * @return {Object} node instance + * @param {number | string} margin margin + * @returns {NodeInstanceWrapper} node instance wrapper */ export const setMargin = margin => node => { setMarginTop(margin)(node); diff --git a/packages/layout/src/node/setOverflow.js b/packages/layout/src/node/setOverflow.js index ab86a1b93..f6af69675 100644 --- a/packages/layout/src/node/setOverflow.js +++ b/packages/layout/src/node/setOverflow.js @@ -6,12 +6,17 @@ const OVERFLOW = { scroll: Yoga.OVERFLOW_SCROLL, }; +/** + * @typedef {Function} NodeInstanceWrapper + * @param {Object} node node instance + * @returns {Object} node instance + */ + /** * Set overflow attribute to node's Yoga instance * - * @param {String} overflow value - * @param {Object} node instance - * @return {Object} node instance + * @param {string} value overflow value + * @returns {NodeInstanceWrapper} node instance wrapper */ const setOverflow = value => node => { const { yogaNode } = node; diff --git a/packages/layout/src/node/setPadding.js b/packages/layout/src/node/setPadding.js index b403803b7..a4ec0a6fc 100644 --- a/packages/layout/src/node/setPadding.js +++ b/packages/layout/src/node/setPadding.js @@ -2,48 +2,53 @@ import Yoga from '../../yoga'; import setYogaValue from './setYogaValue'; +/** + * @typedef {Function} NodeInstanceWrapper + * @param {Object} node node instance + * @returns {Object} node instance + */ + /** * Set padding top attribute to node's Yoga instance * - * @param {Number} padding top - * @param {Object} node instance - * @return {Object} node instance + * @param {number} padding padding top + * @param {Object} node node instance + * @returns {Object} node instance */ export const setPaddingTop = setYogaValue('padding', Yoga.EDGE_TOP); /** * Set padding right attribute to node's Yoga instance * - * @param {Number} padding right - * @param {Object} node instance - * @return {Object} node instance + * @param {number} padding padding right + * @param {Object} node node instance + * @returns {Object} node instance */ export const setPaddingRight = setYogaValue('padding', Yoga.EDGE_RIGHT); /** * Set padding bottom attribute to node's Yoga instance * - * @param {Number} padding bottom - * @param {Object} node instance - * @return {Object} node instance + * @param {number} padding padding bottom + * @param {Object} node node instance + * @returns {Object} node instance */ export const setPaddingBottom = setYogaValue('padding', Yoga.EDGE_BOTTOM); /** * Set padding left attribute to node's Yoga instance * - * @param {Number} padding left - * @param {Object} node instance - * @return {Object} node instance + * @param {number} padding padding left + * @param {Object} node node instance + * @returns {Object} node instance */ export const setPaddingLeft = setYogaValue('padding', Yoga.EDGE_LEFT); /** * Set all paddings at once * - * @param {Number} margin - * @param {Object} node instance - * @return {Object} node instance + * @param {number | string} padding padding + * @returns {NodeInstanceWrapper} node instance wrapper */ export const setPadding = padding => node => { setPaddingTop(padding)(node); diff --git a/packages/layout/src/node/setPosition.js b/packages/layout/src/node/setPosition.js index 790330300..18b5b5211 100644 --- a/packages/layout/src/node/setPosition.js +++ b/packages/layout/src/node/setPosition.js @@ -2,48 +2,53 @@ import Yoga from '../../yoga'; import setYogaValue from './setYogaValue'; +/** + * @typedef {Function} NodeInstanceWrapper + * @param {Object} node node instance + * @returns {Object} node instance + */ + /** * Set position top attribute to node's Yoga instance * - * @param {Number} position top - * @param {Object} node instance - * @return {Object} node instance + * @param {number} position position top + * @param {Object} node node instance + * @returns {Object} node instance */ export const setPositionTop = setYogaValue('position', Yoga.EDGE_TOP); /** * Set position right attribute to node's Yoga instance * - * @param {Number} position right - * @param {Object} node instance - * @return {Object} node instance + * @param {number} position position right + * @param {Object} node node instance + * @returns {Object} node instance */ export const setPositionRight = setYogaValue('position', Yoga.EDGE_RIGHT); /** * Set position bottom attribute to node's Yoga instance * - * @param {Number} position bottom - * @param {Object} node instance - * @return {Object} node instance + * @param {number} position position bottom + * @param {Object} node node instance + * @returns {Object} node instance */ export const setPositionBottom = setYogaValue('position', Yoga.EDGE_BOTTOM); /** * Set position left attribute to node's Yoga instance * - * @param {Number} position left - * @param {Object} node instance - * @return {Object} node instance + * @param {number} position position left + * @param {Object} node node instance + * @returns {Object} node instance */ export const setPositionLeft = setYogaValue('position', Yoga.EDGE_LEFT); /** * Set all positions at once * - * @param {Number} position - * @param {Object} node instance - * @return {Object} node instance + * @param {number | string} position position + * @returns {NodeInstanceWrapper} node instance wrapper */ export const setPosition = position => node => { setPositionTop(position)(node); diff --git a/packages/layout/src/node/setPositionType.js b/packages/layout/src/node/setPositionType.js index 69761ea98..2bea62248 100644 --- a/packages/layout/src/node/setPositionType.js +++ b/packages/layout/src/node/setPositionType.js @@ -1,12 +1,17 @@ import { isNil } from '@react-pdf/fns'; import Yoga from '../../yoga'; +/** + * @typedef {Function} NodeInstanceWrapper + * @param {Object} node node instance + * @returns {Object} node instance + */ + /** * Set position type attribute to node's Yoga instance * - * @param {String} position type - * @param {Object} node instance - * @return {Object} node instance + * @param {string} value position position type + * @returns {NodeInstanceWrapper} node instance wrapper */ const setPositionType = value => node => { const { yogaNode } = node; diff --git a/packages/layout/src/node/setYogaValue.js b/packages/layout/src/node/setYogaValue.js index cbb842500..5ce578ea4 100644 --- a/packages/layout/src/node/setYogaValue.js +++ b/packages/layout/src/node/setYogaValue.js @@ -1,14 +1,24 @@ /* eslint-disable no-unused-expressions */ import { isNil, upperFirst, matchPercent } from '@react-pdf/fns'; +/** + * @typedef {Function} NodeInstanceWrapper + * @param {Object} node node instance + * @returns {Object} node instance + */ + +/** + * @typedef {Function} YogaValueSetter + * @param {any} value + * @returns {NodeInstanceWrapper} node instance wrapper + */ + /** * Set generic yoga attribute to node's Yoga instance, handing `auto`, edges and percentage cases * - * @param {String} property - * @param {Number} edge - * @param {any} value - * @param {Object} node instance - * @return {Object} node instance + * @param {string} attr property + * @param {number} [edge] edge + * @returns {YogaValueSetter} node instance wrapper */ const setYogaValue = (attr, edge) => value => node => { const { yogaNode } = node; diff --git a/packages/layout/src/page/getOrientation.js b/packages/layout/src/page/getOrientation.js index 28ad34a3c..6cb49b364 100644 --- a/packages/layout/src/page/getOrientation.js +++ b/packages/layout/src/page/getOrientation.js @@ -3,10 +3,10 @@ const VALID_ORIENTATIONS = ['portrait', 'landscape']; /** * Get page orientation. Defaults to portrait * - * @param { Object } page object - * @returns { String } page orientation + * @param {Object} page object + * @returns {string} page orientation */ -const getOrientation = page => { +const getOrientation = (page) => { const value = page.props?.orientation || 'portrait'; return VALID_ORIENTATIONS.includes(value) ? value : 'portrait'; }; diff --git a/packages/layout/src/page/getSize.js b/packages/layout/src/page/getSize.js index 85405bef0..76ee76aa6 100644 --- a/packages/layout/src/page/getSize.js +++ b/packages/layout/src/page/getSize.js @@ -57,25 +57,25 @@ const PAGE_SIZES = { /** * Transforms array into size object * - * @param {Array} array - * @returns {Object} size object with width and height + * @param {number[]} v array + * @returns {{ width: number, height: number }} size object with width and height */ -const toSizeObject = v => ({ width: v[0], height: v[1] }); +const toSizeObject = (v) => ({ width: v[0], height: v[1] }); /** * Flip size object * - * @param {Object} size object - * @returns {Object} flipped size object + * @param {{ width: number, height: number }} v size object + * @returns {{ width: number, height: number }} flipped size object */ -const flipSizeObject = v => ({ width: v.height, height: v.width }); +const flipSizeObject = (v) => ({ width: v.height, height: v.width }); /** * Adjust page size to passed DPI * - * @param {Object} size object - * @param {number} dpi - * @returns {Object} adjusted size object + * @param {{ width: number, height: number }} v size object + * @param {number} dpi DPI + * @returns {{ width: number, height: number }} adjusted size object */ const adjustDpi = (v, dpi) => ({ width: v.width ? v.width * dpi : v.width, @@ -85,34 +85,37 @@ const adjustDpi = (v, dpi) => ({ /** * Returns size object from a given string * - * @param {String} page size string - * @returns {Object} size object with width and height + * @param {string} v page size string + * @returns {{ width: number, height: number }} size object with width and height */ -const getStringSize = v => { +const getStringSize = (v) => { return toSizeObject(PAGE_SIZES[v.toUpperCase()]); }; /** * Returns size object from a single number * - * @param {Number} page size number - * @returns {Object} size object with width and height + * @param {number} n page size number + * @returns {{ width: number, height: number }} size object with width and height */ -const getNumberSize = n => toSizeObject([n]); +const getNumberSize = (n) => toSizeObject([n]); /** * Return page size in an object { width, height } * * @param {Object} page instance - * @returns {Object} size object with width and height + * @returns {{ width: number, height: number }} size object with width and height */ -const getSize = page => { +const getSize = (page) => { const value = page.props?.size || 'A4'; const dpi = parseFloat(page.props?.dpi || 72); const type = typeof value; - let size = value; + /** + * @type {{ width: number, height: number }} + */ + let size; if (type === 'string') { size = getStringSize(value); @@ -120,6 +123,8 @@ const getSize = page => { size = toSizeObject(value); } else if (type === 'number') { size = getNumberSize(value); + } else { + size = value; } size = adjustDpi(size, dpi / 72); diff --git a/packages/layout/src/page/isHeightAuto.js b/packages/layout/src/page/isHeightAuto.js index 7eb221273..589072247 100644 --- a/packages/layout/src/page/isHeightAuto.js +++ b/packages/layout/src/page/isHeightAuto.js @@ -4,7 +4,7 @@ import { isNil } from '@react-pdf/fns'; * Checks if page has auto height * * @param {Object} page - * @returns {Boolean} is page height auto + * @returns {boolean} is page height auto */ const isHeightAuto = page => isNil(page.box?.height); diff --git a/packages/layout/src/page/isLandscape.js b/packages/layout/src/page/isLandscape.js index ac3f7eeac..84568ae1a 100644 --- a/packages/layout/src/page/isLandscape.js +++ b/packages/layout/src/page/isLandscape.js @@ -4,7 +4,7 @@ import getOrientation from './getOrientation'; * Return true if page is landscape * * @param {Object} page instance - * @returns {Boolean} is page landscape + * @returns {boolean} is page landscape */ const isLandscape = page => getOrientation(page) === 'landscape'; diff --git a/packages/layout/src/page/isPortrait.js b/packages/layout/src/page/isPortrait.js index 87323e210..5978ad519 100644 --- a/packages/layout/src/page/isPortrait.js +++ b/packages/layout/src/page/isPortrait.js @@ -4,7 +4,7 @@ import getOrientation from './getOrientation'; * Return true if page is portrait * * @param {Object} page instance - * @returns {Boolean} is page portrait + * @returns {boolean} is page portrait */ const isPortrait = page => getOrientation(page) === 'portrait'; diff --git a/packages/layout/src/steps/resolveAssets.js b/packages/layout/src/steps/resolveAssets.js index 89a3b3412..dd5ccdf30 100644 --- a/packages/layout/src/steps/resolveAssets.js +++ b/packages/layout/src/steps/resolveAssets.js @@ -3,13 +3,14 @@ import * as P from '@react-pdf/primitives'; import fetchEmojis from '../text/emoji'; import fetchImage from '../image/fetchImage'; -const isImage = node => node.type === P.Image; +const isImage = (node) => node.type === P.Image; /** * Get all asset promises that need to be resolved * - * @param {Object} root node - * @returns {Array} asset promises + * @param {Object} fontStore font store + * @param {Object} node root node + * @returns {Promise[]} asset promises */ const fetchAssets = (fontStore, node) => { const promises = []; @@ -36,7 +37,7 @@ const fetchAssets = (fontStore, node) => { } if (n.children) { - n.children.forEach(childNode => { + n.children.forEach((childNode) => { listToExplore.push(childNode); }); } @@ -49,9 +50,9 @@ const fetchAssets = (fontStore, node) => { * Fetch image, font and emoji assets in parallel. * Layout process will not be resumed until promise resolves. * - * @param {Object} root node + * @param {Object} node root node * @param {Object} fontStore font store - * @returns {Object} root node + * @returns {Promise} root node */ const resolveAssets = async (node, fontStore) => { const promises = fetchAssets(fontStore, node); diff --git a/packages/layout/src/steps/resolveDimensions.js b/packages/layout/src/steps/resolveDimensions.js index dc3e9d099..2190e727c 100644 --- a/packages/layout/src/steps/resolveDimensions.js +++ b/packages/layout/src/steps/resolveDimensions.js @@ -125,12 +125,17 @@ const setYogaValues = node => { )(node); }; +/** + * @typedef {Function} InsertYogaNodes + * @param {Object} child child node + * @returns {Object} node + */ + /** * Inserts child into parent' yoga node * - * @param {Object} parent - * @param {Object} node - * @param {Object} node + * @param {Object} parent parent + * @returns {InsertYogaNodes} insert yoga nodes */ const insertYogaNodes = parent => child => { parent.insertChild(child.yogaNode, parent.getChildCount()); @@ -161,12 +166,17 @@ const setMeasureFunc = (node, page, fontStore) => { const isLayoutElement = node => !isText(node) && !isNote(node) && !isSvg(node); +/** + * @typedef {Function} CreateYogaNodes + * @param {Object} node + * @returns {Object} node with appended yoga node + */ + /** * Creates and add yoga node to document tree * Handles measure function for text and image nodes * - * @param {Object} node - * @returns {Object} node with appended yoga node + * @returns {CreateYogaNodes} create yoga nodes */ const createYogaNodes = (page, fontStore) => node => { const yogaNode = Yoga.Node.createWithConfig(YOGA_CONFIG); @@ -192,8 +202,8 @@ const createYogaNodes = (page, fontStore) => node => { /** * Performs yoga calculation * - * @param {Object} node - * @returns {Object} node + * @param {Object} page page node + * @returns {Object} page node */ const calculateLayout = page => { page.yogaNode.calculateLayout(); @@ -278,7 +288,8 @@ export const resolvePageDimensions = (page, fontStore) => { /** * Calculates root object layout using Yoga. * - * @param {Object} root object + * @param {Object} node root object + * @param {Object} fontStore font store * @returns {Object} root object with correct 'box' layout attributes */ const resolveDimensions = (node, fontStore) => { diff --git a/packages/layout/src/steps/resolveInheritance.js b/packages/layout/src/steps/resolveInheritance.js index 182465eb7..5b9701017 100644 --- a/packages/layout/src/steps/resolveInheritance.js +++ b/packages/layout/src/steps/resolveInheritance.js @@ -54,12 +54,17 @@ const merge = (inheritedStyles, style) => { }; /** - * Merges styles with node - * - * @param {Object} style object + * @typedef {Function} MergeStyles * @param {Object} node * @returns {Object} node with styles merged */ + +/** + * Merges styles with node + * + * @param {Object} inheritedStyles style object + * @returns {MergeStyles} merge styles function + */ const mergeStyles = inheritedStyles => node => { const style = merge(inheritedStyles, node.style || {}); return Object.assign({}, node, { style }); @@ -68,7 +73,7 @@ const mergeStyles = inheritedStyles => node => { /** * Inherit style values from the root to the leafs * - * @param {Object} document root + * @param {Object} node document root * @returns {Object} document root with inheritance * */ diff --git a/packages/layout/src/steps/resolveLinkSubstitution.js b/packages/layout/src/steps/resolveLinkSubstitution.js index 01e643c14..f459d204d 100644 --- a/packages/layout/src/steps/resolveLinkSubstitution.js +++ b/packages/layout/src/steps/resolveLinkSubstitution.js @@ -13,7 +13,7 @@ const isTextInstance = isType(P.TextInstance); * Checks if node has render prop * * @param {Object} node - * @returns {Boolean} has render prop? + * @returns {boolean} has render prop? */ const hasRenderProp = node => !!node.props?.render; @@ -21,7 +21,7 @@ const hasRenderProp = node => !!node.props?.render; * Checks if node is text type (Text or TextInstance) * * @param {Object} node - * @returns {Boolean} are all children text instances? + * @returns {boolean} are all children text instances? */ const isTextType = node => isText(node) || isTextInstance(node); @@ -29,7 +29,7 @@ const isTextType = node => isText(node) || isTextInstance(node); * Checks if is tet link that needs to be wrapped in Text * * @param {Object} node - * @returns {Boolean} are all children text instances? + * @returns {boolean} are all children text instances? */ const isTextLink = node => { const children = node.children || []; @@ -47,7 +47,7 @@ const isTextLink = node => { * Wraps node children inside Text node * * @param {Object} node - * @returns {Boolean} node with intermediate Text child + * @returns {boolean} node with intermediate Text child */ const wrapText = node => { const textElement = { diff --git a/packages/layout/src/steps/resolveOrigins.js b/packages/layout/src/steps/resolveOrigins.js index cb8820be6..112a259d3 100644 --- a/packages/layout/src/steps/resolveOrigins.js +++ b/packages/layout/src/steps/resolveOrigins.js @@ -21,8 +21,8 @@ const resolveNodeOrigin = node => { /** * Resolve document origins * - * @param {Object} document root - * @returns {Object} documrnt root + * @param {Object} root document root + * @returns {Object} document root */ const resolveOrigin = root => { diff --git a/packages/layout/src/steps/resolvePagePaddings.js b/packages/layout/src/steps/resolvePagePaddings.js index cd38c3554..1881ce9a1 100644 --- a/packages/layout/src/steps/resolvePagePaddings.js +++ b/packages/layout/src/steps/resolvePagePaddings.js @@ -1,25 +1,35 @@ import { evolve, matchPercent } from '@react-pdf/fns'; -/* +/** + * @typedef {Function} ResolvePageHorizontalPadding + * @param {string} value padding value + * @returns {Object} translated padding value + */ + +/** * Translates page percentage horizontal paddings in fixed ones * - * @param {Object} page container - * @param {String} padding value - * @returns {Object} translated padding value + * @param {Object} container page container + * @returns {ResolvePageHorizontalPadding} resolve page horizontal padding */ -const resolvePageHorizontalPadding = container => value => { +const resolvePageHorizontalPadding = (container) => (value) => { const match = matchPercent(value); return match ? match.percent * container.width : value; }; +/** + * @typedef {Function} ResolvePageVerticalPadding + * @param {string} padding value + * @returns {Object} translated padding value + */ + /** * Translates page percentage vertical paddings in fixed ones * - * @param {Object} page container - * @param {String} padding value - * @returns {Object} translated padding value + * @param {Object} container page container + * @returns {ResolvePageVerticalPadding} resolve page vertical padding */ -const resolvePageVerticalPadding = container => value => { +const resolvePageVerticalPadding = (container) => (value) => { const match = matchPercent(value); return match ? match.percent * container.height : value; }; @@ -30,7 +40,7 @@ const resolvePageVerticalPadding = container => value => { * @param {Object} page * @returns {Object} page with fixed paddings */ -const resolvePagePaddings = page => { +const resolvePagePaddings = (page) => { const container = page.style; const style = evolve( @@ -51,10 +61,10 @@ const resolvePagePaddings = page => { * This has to be computed from pages calculated size and not by Yoga * because at this point we didn't performed pagination yet. * - * @param {Object} document root + * @param {Object} root document root * @returns {Object} document root with translated page paddings */ -const resolvePagesPaddings = root => { +const resolvePagesPaddings = (root) => { if (!root.children) return root; const children = root.children.map(resolvePagePaddings); diff --git a/packages/layout/src/steps/resolvePageSizes.js b/packages/layout/src/steps/resolvePageSizes.js index d24aa4522..82ac43872 100644 --- a/packages/layout/src/steps/resolvePageSizes.js +++ b/packages/layout/src/steps/resolvePageSizes.js @@ -17,7 +17,7 @@ export const resolvePageSize = page => { /** * Resolves page sizes * - * @param {Object} document root + * @param {Object} root document root * @returns {Object} document root with resolved page sizes */ const resolvePageSizes = root => { diff --git a/packages/layout/src/steps/resolvePagination.js b/packages/layout/src/steps/resolvePagination.js index a87e26ee7..00b242486 100644 --- a/packages/layout/src/steps/resolvePagination.js +++ b/packages/layout/src/steps/resolvePagination.js @@ -18,19 +18,19 @@ import resolveInheritance from './resolveInheritance'; import { resolvePageDimensions } from './resolveDimensions'; import resolveAssets from './resolveAssets'; -const isText = node => node.type === P.Text; +const isText = (node) => node.type === P.Text; // Prevent splitting elements by low decimal numbers -const SAFTY_THRESHOLD = 0.001; +const SAFETY_THRESHOLD = 0.001; const assingChildren = (children, node) => Object.assign({}, node, { children }); -const getTop = node => node.box?.top || 0; +const getTop = (node) => node.box?.top || 0; -const allFixed = nodes => nodes.every(isFixed); +const allFixed = (nodes) => nodes.every(isFixed); -const isDynamic = node => !isNil(node.props?.render); +const isDynamic = (node) => !isNil(node.props?.render); const relayoutPage = asyncCompose( resolveAssets, @@ -39,7 +39,7 @@ const relayoutPage = asyncCompose( resolvePageDimensions, ); -const warnUnavailableSpace = node => { +const warnUnavailableSpace = (node) => { console.warn( `Node of type ${node.type} can't wrap between pages and it's bigger than available page height`, ); @@ -58,7 +58,7 @@ const splitNodes = (height, contentArea, nodes) => { const nodeHeight = child.box.height; const isOutside = height <= nodeTop; const shouldBreak = shouldNodeBreak(child, futureNodes, height); - const shouldSplit = height + SAFTY_THRESHOLD < nodeTop + nodeHeight; + const shouldSplit = height + SAFETY_THRESHOLD < nodeTop + nodeHeight; const canWrap = canNodeWrap(child); const fitsInsidePage = nodeHeight <= contentArea; @@ -145,7 +145,7 @@ const splitView = (node, height, contentArea) => { const split = (node, height, contentArea) => isText(node) ? splitText(node, height) : splitView(node, height, contentArea); -const shouldResolveDynamicNodes = node => { +const shouldResolveDynamicNodes = (node) => { const children = node.children || []; return isDynamic(node) || children.some(shouldResolveDynamicNodes); }; @@ -159,10 +159,10 @@ const resolveDynamicNodes = (props, node) => { const res = node.props.render(props); return createInstances(res) .filter(Boolean) - .map(n => resolveDynamicNodes(props, n)); + .map((n) => resolveDynamicNodes(props, n)); } - return children.map(c => resolveDynamicNodes(props, c)); + return children.map((c) => resolveDynamicNodes(props, c)); }; // We reset dynamic text box so it can be computed again later on @@ -276,7 +276,7 @@ const paginate = async (page, pageNumber, fontStore) => { * Performs pagination. This is the step responsible for breaking the whole document * into pages following pagination rules, such as `fixed`, `break` and dynamic nodes. * - * @param {Object} node + * @param {Object} doc node * @param {Object} fontStore font store * @returns {Object} layout node */ diff --git a/packages/layout/src/steps/resolvePercentHeight.js b/packages/layout/src/steps/resolvePercentHeight.js index 134092ce6..4cd27e90f 100644 --- a/packages/layout/src/steps/resolvePercentHeight.js +++ b/packages/layout/src/steps/resolvePercentHeight.js @@ -3,8 +3,8 @@ import { isNil, matchPercent } from '@react-pdf/fns'; /** * Transform percent height into fixed * - * @param {String | number} height - * @return {number} height + * @param {number} height + * @returns {number} height */ const transformHeight = (pageArea, height) => { const match = matchPercent(height); @@ -15,7 +15,7 @@ const transformHeight = (pageArea, height) => { * Get page area (height minus paddings) * * @param {Object} page - * @return {number} page area + * @returns {number} page area */ const getPageArea = page => { const pageHeight = page.style.height; @@ -30,7 +30,7 @@ const getPageArea = page => { * * @param {Object} page * @param {Object} node - * @return {Object} transformed node + * @returns {Object} transformed node */ const resolveNodePercentHeight = (page, node) => { if (isNil(page.style?.height)) return node; @@ -47,7 +47,7 @@ const resolveNodePercentHeight = (page, node) => { * Transform page immediate children with percent height to fixed * * @param {Object} page - * @return {Object} transformed page + * @returns {Object} transformed page */ const resolvePagePercentHeight = page => { if (!page.children) return page; @@ -62,8 +62,8 @@ const resolvePagePercentHeight = page => { * Transform all page immediate children with percent height to fixed. * This is needed for computing correct dimensions on pre-pagination layout. * - * @param {Object} document root - * @return {Object} transformed document root + * @param {Object} root document root + * @returns {Object} transformed document root */ const resolvePercentHeight = root => { if (!root.children) return root; diff --git a/packages/layout/src/steps/resolvePercentRadius.js b/packages/layout/src/steps/resolvePercentRadius.js index 02e5af938..ba38b0e8c 100644 --- a/packages/layout/src/steps/resolvePercentRadius.js +++ b/packages/layout/src/steps/resolvePercentRadius.js @@ -1,12 +1,17 @@ import { evolve, matchPercent } from '@react-pdf/fns'; +/** + * @typedef {Function} ResolveRadius + * @param {string | number} value border radius value + * @returns {number} resolved radius value + */ + /** * - * @param {Object} container width and height - * @param {String | Number} value border radius value - * @returns {Number} fixed border radius value + * @param {{ width: number, height: number }} container width and height + * @returns {ResolveRadius} resolve radius function */ -const resolveRadius = container => value => { +const resolveRadius = (container) => (value) => { if (!value) return undefined; const match = matchPercent(value); @@ -22,7 +27,7 @@ const resolveRadius = container => value => { * @param {Object} node * @returns {Object} node */ -const resolvePercentRadius = node => { +const resolvePercentRadius = (node) => { const style = evolve( { borderTopLeftRadius: resolveRadius(node.box), diff --git a/packages/layout/src/steps/resolveStyles.js b/packages/layout/src/steps/resolveStyles.js index 46b23a877..33f7a6e9b 100644 --- a/packages/layout/src/steps/resolveStyles.js +++ b/packages/layout/src/steps/resolveStyles.js @@ -12,7 +12,7 @@ const DEFAULT_LINK_STYLES = { * Computes styles using stylesheet * * @param {Object} container - * @param {Object} document node + * @param {Object} node document node * @returns {Object} computed styles */ const computeStyle = (container, node) => { @@ -27,12 +27,17 @@ const computeStyle = (container, node) => { return stylesheet(container, baseStyle); }; +/** + * @typedef {Function} ResolveNodeStyles + * @param {Object} node document node + * @returns {Object} node (and subnodes) with resolved styles + */ + /** * Resolves node styles * * @param {Object} container - * @param {Object} document node - * @returns {Object} node (and subnodes) with resolved styles + * @returns {ResolveNodeStyles} resolve node styles */ const resolveNodeStyles = container => node => { const style = computeStyle(container, node); @@ -47,7 +52,7 @@ const resolveNodeStyles = container => node => { /** * Resolves page styles * - * @param {Object} document page + * @param {Object} page document page * @returns {Object} document page with resolved styles */ const resolvePageStyles = page => { @@ -63,7 +68,7 @@ const resolvePageStyles = page => { /** * Resolves document styles * - * @param {Object} document root + * @param {Object} root document root * @returns {Object} document root with resolved styles */ const resolveStyles = root => { diff --git a/packages/layout/src/steps/resolveSvg.js b/packages/layout/src/steps/resolveSvg.js index f41dcbab6..b1b934be5 100644 --- a/packages/layout/src/steps/resolveSvg.js +++ b/packages/layout/src/steps/resolveSvg.js @@ -192,7 +192,7 @@ const resolveSvgRoot = (node, fontStore) => { /** * Pre-process SVG nodes so they can be rendered in the next steps * - * @param {Object} root node + * @param {Object} node root node * @param {Object} fontStore font store * @returns {Object} root node */ diff --git a/packages/layout/src/svg/measureSvg.js b/packages/layout/src/svg/measureSvg.js index 74b5525bd..cd5c073ca 100644 --- a/packages/layout/src/svg/measureSvg.js +++ b/packages/layout/src/svg/measureSvg.js @@ -1,41 +1,42 @@ import Yoga from '../../yoga'; -const getAspectRatio = viewbox => { +const getAspectRatio = (viewbox) => { if (!viewbox) return null; return (viewbox.maxX - viewbox.minX) / (viewbox.maxY - viewbox.minY); }; +/** + * @typedef {Function} MeasureSvg + * @param {number} width + * @param {number} widthMode + * @param {number} height + * @param {number} heightMode + * @returns {{ width: number, height: number }} svg width and height + */ + /** * Yoga svg measure function * * @param {Object} page * @param {Object} node - * @param {Number} width - * @param {Number} widthMode - * @param {Number} height - * @param {Number} heightMode - * @returns {Object} canvas width and height + * @returns {MeasureSvg} measure svg */ -const measureCanvas = (page, node) => ( - width, - widthMode, - height, - heightMode, -) => { - const aspectRatio = getAspectRatio(node.props.viewBox) || 1; +const measureCanvas = + (page, node) => (width, widthMode, height, heightMode) => { + const aspectRatio = getAspectRatio(node.props.viewBox) || 1; - if ( - widthMode === Yoga.MEASURE_MODE_EXACTLY || - widthMode === Yoga.MEASURE_MODE_AT_MOST - ) { - return { width, height: width / aspectRatio }; - } + if ( + widthMode === Yoga.MEASURE_MODE_EXACTLY || + widthMode === Yoga.MEASURE_MODE_AT_MOST + ) { + return { width, height: width / aspectRatio }; + } - if (heightMode === Yoga.MEASURE_MODE_EXACTLY) { - return { width: height * aspectRatio }; - } + if (heightMode === Yoga.MEASURE_MODE_EXACTLY) { + return { width: height * aspectRatio }; + } - return {}; -}; + return {}; + }; export default measureCanvas; diff --git a/packages/layout/src/text/fromFragments.js b/packages/layout/src/text/fromFragments.js index cca715ebe..501819928 100644 --- a/packages/layout/src/text/fromFragments.js +++ b/packages/layout/src/text/fromFragments.js @@ -1,15 +1,15 @@ /** * Create attributed string from text fragments * - * @param {Array} fragments - * @return {Object} attributed string + * @param {Object[]} fragments fragments + * @returns {Object} attributed string */ -const fromFragments = fragments => { +const fromFragments = (fragments) => { let offset = 0; let string = ''; const runs = []; - fragments.forEach(fragment => { + fragments.forEach((fragment) => { string += fragment.string; runs.push({ diff --git a/packages/layout/src/text/getAttributedString.js b/packages/layout/src/text/getAttributedString.js index 1a9858949..6b1b361ea 100644 --- a/packages/layout/src/text/getAttributedString.js +++ b/packages/layout/src/text/getAttributedString.js @@ -7,16 +7,18 @@ import transformText from './transformText'; const PREPROCESSORS = [ignoreChars, embedEmojis]; -const isImage = node => node.type === P.Image; +const isImage = (node) => node.type === P.Image; -const isTextInstance = node => node.type === P.TextInstance; +const isTextInstance = (node) => node.type === P.TextInstance; /** * Get textkit fragments of given node object * - * @param {Object} font store + * @param {Object} fontStore font store * @param {Object} instance node - * @returns {Array} text fragments + * @param {string} [parentLink] parent link + * @param {number} [level] fragment level + * @returns {Object[]} text fragments */ const getFragments = (fontStore, instance, parentLink, level = 0) => { if (!instance) return [{ string: '' }]; @@ -112,7 +114,7 @@ const getFragments = (fontStore, instance, parentLink, level = 0) => { /** * Get textkit attributed string from text node * - * @param {Object} font store + * @param {Object} fontStore font store * @param {Object} instance node * @returns {Object} attributed string */ diff --git a/packages/layout/src/text/heightAtLineIndex.js b/packages/layout/src/text/heightAtLineIndex.js index 0c7c8fb99..e57f4c803 100644 --- a/packages/layout/src/text/heightAtLineIndex.js +++ b/packages/layout/src/text/heightAtLineIndex.js @@ -2,7 +2,7 @@ * Get height for given text line index * * @param {Object} node - * @param {Number} index + * @param {number} index */ const heightAtLineIndex = (node, index) => { let counter = 0; diff --git a/packages/layout/src/text/layoutText.js b/packages/layout/src/text/layoutText.js index 35a822183..1a9e1b681 100644 --- a/packages/layout/src/text/layoutText.js +++ b/packages/layout/src/text/layoutText.js @@ -20,15 +20,15 @@ const engines = { const engine = layoutEngine(engines); -const getMaxLines = node => node.style?.maxLines; +const getMaxLines = (node) => node.style?.maxLines; -const getTextOverflow = node => node.style?.textOverflow; +const getTextOverflow = (node) => node.style?.textOverflow; /** * Get layout container for specific text node * - * @param {Number} width - * @param {Number} height + * @param {number} width + * @param {number} height * @param {Object} node * @returns {Object} layout container */ @@ -64,11 +64,11 @@ const getLayoutOptions = (fontStore, node) => ({ /** * Get text lines for given node * - * @param {Object} node - * @param {Number} container width - * @param {Number} container height - * @param {Number} fontStore font store - * @returns {Array} layout lines + * @param {Object} node node + * @param {number} width container width + * @param {number} height container height + * @param {number} fontStore font store + * @returns {Object[]} layout lines */ const layoutText = (node, width, height, fontStore) => { const attributedString = getAttributedString(fontStore, node); diff --git a/packages/layout/src/text/lineIndexAtHeight.js b/packages/layout/src/text/lineIndexAtHeight.js index e77ed2843..b49dd9d2b 100644 --- a/packages/layout/src/text/lineIndexAtHeight.js +++ b/packages/layout/src/text/lineIndexAtHeight.js @@ -2,7 +2,7 @@ * Get line index at given height * * @param {Object} node - * @param {Number} height + * @param {number} height */ const lineIndexAtHeight = (node, height) => { let y = 0; diff --git a/packages/layout/src/text/linesHeight.js b/packages/layout/src/text/linesHeight.js index 3159b8b32..057660b4c 100644 --- a/packages/layout/src/text/linesHeight.js +++ b/packages/layout/src/text/linesHeight.js @@ -2,9 +2,9 @@ * Get lines height (if any) * * @param {Object} node - * @returns {Number} lines height + * @returns {number} lines height */ -const linesHeight = node => { +const linesHeight = (node) => { if (!node.lines) return -1; return node.lines.reduce((acc, line) => acc + line.box.height, 0); }; diff --git a/packages/layout/src/text/linesWidth.js b/packages/layout/src/text/linesWidth.js index 775b352fa..86f154f7d 100644 --- a/packages/layout/src/text/linesWidth.js +++ b/packages/layout/src/text/linesWidth.js @@ -2,12 +2,12 @@ * Get lines width (if any) * * @param {Object} node - * @returns {Number} lines width + * @returns {number} lines width */ -const linesWidth = node => { +const linesWidth = (node) => { if (!node.lines) return 0; - return Math.max(0, ...node.lines.map(line => line.xAdvance)); + return Math.max(0, ...node.lines.map((line) => line.xAdvance)); }; export default linesWidth; diff --git a/packages/layout/src/text/measureText.js b/packages/layout/src/text/measureText.js index 8b9e5f658..6cedcbdee 100644 --- a/packages/layout/src/text/measureText.js +++ b/packages/layout/src/text/measureText.js @@ -8,16 +8,21 @@ import linesHeight from './linesHeight'; const ALIGNMENT_FACTORS = { center: 0.5, right: 1 }; +/** + * @typedef {Function} MeasureText + * @param {number} width + * @param {number} widthMode + * @param {number} height + * @returns {{ width: number, height: number }} text width and height + */ + /** * Yoga text measure function * * @param {Object} page * @param {Object} node - * @param {Number} width - * @param {Number} widthMode - * @param {Number} height - * @param {Number} heightMode - * @returns {Object} text width and height + * @param {Object} fontStore + * @returns {MeasureText} measure text function */ const measureText = (page, node, fontStore) => (width, widthMode, height) => { if (widthMode === Yoga.MEASURE_MODE_EXACTLY) { diff --git a/packages/layout/src/text/transformText.js b/packages/layout/src/text/transformText.js index 1044a1255..fc25c8f96 100644 --- a/packages/layout/src/text/transformText.js +++ b/packages/layout/src/text/transformText.js @@ -3,9 +3,9 @@ import { capitalize, upperFirst } from '@react-pdf/fns'; /** * Apply transformation to text string * - * @param {String} text - * @param {String} transformation type - * @returns {String} transformed text + * @param {string} text + * @param {string} transformation type + * @returns {string} transformed text */ const transformText = (text, transformation) => { switch (transformation) { diff --git a/packages/pdfkit/src/document.js b/packages/pdfkit/src/document.js index 472d8169d..34a9d6cb2 100644 --- a/packages/pdfkit/src/document.js +++ b/packages/pdfkit/src/document.js @@ -323,9 +323,36 @@ class PDFDocument extends stream.Readable { toString() { return '[object PDFDocument]'; } + + initColor() {} + + initVector() {} + + initFonts() {} + + initText() {} + + initImages() {} + + initOutline() {} + + /** + * @param {number} m11 + * @param {number} m12 + * @param {number} m21 + * @param {number} m22 + * @param {number} dx + * @param {number} dy + */ + // eslint-disable-next-line no-unused-vars + transform(m11, m12, m21, m22, dx, dy) {} + + endOutline() {} + + endAcroForm() {} } -const mixin = methods => { +const mixin = (methods) => { Object.assign(PDFDocument.prototype, methods); }; diff --git a/packages/pdfkit/src/mixins/text.js b/packages/pdfkit/src/mixins/text.js index 4def10dd6..c04a501da 100644 --- a/packages/pdfkit/src/mixins/text.js +++ b/packages/pdfkit/src/mixins/text.js @@ -58,7 +58,10 @@ export default { x = null; } - // clone options object + // shallow clone options object + /** + * @type {Object} + */ const result = Object.assign({}, options); // extend options with previous values for continued text @@ -152,7 +155,7 @@ export default { } // Adds a segment of text to the TJ command buffer - const addSegment = cur => { + const addSegment = (cur) => { if (last < cur) { const hex = encoded.slice(last, cur).join(''); const advance = @@ -164,7 +167,7 @@ export default { }; // Flushes the current TJ commands to the output stream - const flush = i => { + const flush = (i) => { addSegment(i); if (commands.length > 0) { diff --git a/packages/pdfkit/src/tree.js b/packages/pdfkit/src/tree.js index e64aa68f7..2ac65ac00 100644 --- a/packages/pdfkit/src/tree.js +++ b/packages/pdfkit/src/tree.js @@ -53,7 +53,12 @@ class PDFTree { return out.join('\n'); } - _compareKeys() { + /** + * @param {string} a + * @param {string} b + * @returns {number} + */ + _compareKeys(a, b) { throw new Error('Must be implemented by subclasses'); } @@ -61,7 +66,10 @@ class PDFTree { throw new Error('Must be implemented by subclasses'); } - _dataForKey() { + /** + * @param {string} key + */ + _dataForKey(key) { throw new Error('Must be implemented by subclasses'); } } diff --git a/packages/render/src/svg/parsePoints.js b/packages/render/src/svg/parsePoints.js index 369480115..50323886f 100644 --- a/packages/render/src/svg/parsePoints.js +++ b/packages/render/src/svg/parsePoints.js @@ -1,3 +1,10 @@ +/** + * Create pairs from array + * + * @template T + * @param {T[]} values array + * @returns {T[][]} pairs + */ const pairs = values => { const result = []; @@ -11,8 +18,8 @@ const pairs = values => { /** * Parse svg-like points into number arrays * - * @param {String} points string ex. "20,30 50,60" - * @return {Array} points array ex. [[20, 30], [50, 60]] + * @param {string} points string ex. "20,30 50,60" + * @returns {number[][]} points array ex. [[20, 30], [50, 60]] */ const parsePoints = points => { let values = (points || '') @@ -25,9 +32,9 @@ const parsePoints = points => { values = values.slice(0, -1); } - values = values.map(parseFloat); + const mappedValues = values.map(parseFloat); - return pairs(values); + return pairs(mappedValues); }; export default parsePoints; diff --git a/packages/renderer/src/dom/usePDF.js b/packages/renderer/src/dom/usePDF.js index e78854562..3fb43c023 100644 --- a/packages/renderer/src/dom/usePDF.js +++ b/packages/renderer/src/dom/usePDF.js @@ -5,6 +5,12 @@ import { useState, useRef, useEffect, useCallback } from 'react'; import { pdf } from '../index'; +/** + * PDF hook + * + * @param {Object} [options] hook options + * @returns {[Object, Function]} pdf state and update function + */ export const usePDF = ({ document } = {}) => { const pdfInstance = useRef(null); diff --git a/packages/renderer/src/node/renderTo.js b/packages/renderer/src/node/renderTo.js index 738e2ac4f..6062fa304 100644 --- a/packages/renderer/src/node/renderTo.js +++ b/packages/renderer/src/node/renderTo.js @@ -3,12 +3,21 @@ import { Buffer } from 'buffer'; import { pdf } from '../index'; +/** + * @param {React.ReactElement} element + * @returns {Promise} + */ export const renderToStream = async element => { const instance = pdf(element); const stream = await instance.toBuffer(); return stream; }; +/** + * @param {React.ReactElement} element + * @param {string} filePath + * @param {Function} [callback] + */ export const renderToFile = async (element, filePath, callback) => { const output = await renderToStream(element); const stream = fs.createWriteStream(filePath); @@ -24,6 +33,10 @@ export const renderToFile = async (element, filePath, callback) => { }); }; +/** + * @param {React.ReactElement} element + * @returns {Promise} + */ export const renderToBuffer = element => renderToStream(element).then( stream => diff --git a/packages/renderer/src/utils/propsEqual.js b/packages/renderer/src/utils/propsEqual.js index 265b95cd6..093777945 100644 --- a/packages/renderer/src/utils/propsEqual.js +++ b/packages/renderer/src/utils/propsEqual.js @@ -3,9 +3,9 @@ /** * Checks if two sets of props are equal (recursively) * - * @param {Object} props A - * @param {Object} props B - * @returns {Boolean} props equals? + * @param {Object} a props A + * @param {Object} b props B + * @returns {boolean} props equals? * */ const propsEqual = (a, b) => { diff --git a/packages/renderer/tests/dynamicContent.test.jsx b/packages/renderer/tests/dynamicContent.test.jsx new file mode 100644 index 000000000..1e9c5e8e2 --- /dev/null +++ b/packages/renderer/tests/dynamicContent.test.jsx @@ -0,0 +1,28 @@ +import { describe, expect, test } from 'vitest'; + +import { Document, Image, Page, View } from '@react-pdf/renderer'; +import renderToImage from './renderComponent'; + +const mount = async children => { + const image = await renderToImage( + + {children} + , + ); + + return image; +}; + +describe('dynamic content', () => { + test('should render an image', async () => { + const url = + 'https://user-images.githubusercontent.com/5600341/27505816-c8bc37aa-587f-11e7-9a86-08a2d081a8b9.png'; + const image = await mount( + } + />, + ); + + expect(image).toMatchImageSnapshot(); + }, 10000); +}); diff --git a/packages/renderer/tests/node.test.js b/packages/renderer/tests/node.test.js index 13cb7db7f..85d4e398e 100644 --- a/packages/renderer/tests/node.test.js +++ b/packages/renderer/tests/node.test.js @@ -10,6 +10,9 @@ const { Document, Page, View } = ReactPDF; const __dirname = path.dirname(url.fileURLToPath(import.meta.url)); +/** + * @param {Object} props + */ const TestDocument = ({ onRender }) => { return ( diff --git a/packages/renderer/tests/snapshots/dynamic-content-test-jsx-tests-dynamic-content-test-jsx-dynamic-content-should-render-an-image-1-snap.png b/packages/renderer/tests/snapshots/dynamic-content-test-jsx-tests-dynamic-content-test-jsx-dynamic-content-should-render-an-image-1-snap.png new file mode 100644 index 0000000000000000000000000000000000000000..dbb477f1fb801d2236ad19dc3cf051354b1b7d17 GIT binary patch literal 20778 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 UF&9h0<%h>iuUZ<_8r(_zFPi={&j0`b literal 0 HcmV?d00001 diff --git a/packages/stylesheet/src/expand/boxModel.js b/packages/stylesheet/src/expand/boxModel.js index e2d398d24..3ceb677e5 100644 --- a/packages/stylesheet/src/expand/boxModel.js +++ b/packages/stylesheet/src/expand/boxModel.js @@ -18,6 +18,12 @@ const logError = (style, value) => { `); }; +/** + * @param {Object} options + * @param {Function} [options.expandsTo] + * @param {number} [options.maxValues] + * @param {boolean} [options.autoSupported] + */ const expandBoxModel = ({ expandsTo, maxValues = 1, diff --git a/packages/stylesheet/src/expand/flex.js b/packages/stylesheet/src/expand/flex.js index edc4873f0..b80693ef5 100644 --- a/packages/stylesheet/src/expand/flex.js +++ b/packages/stylesheet/src/expand/flex.js @@ -2,9 +2,15 @@ // TODO: change flex defaults to [0, 1, 'auto'] as in spec in next major release const flexDefaults = [1, 1, 0]; +/** + * @type {(number | 'auto')[]} + */ const flexAuto = [1, 1, 'auto']; const expandFlex = (key, value) => { + /** + * @type {(number | 'auto')[]} + */ let defaults = flexDefaults; let matches = []; if (value === 'auto') { diff --git a/packages/stylesheet/src/expand/index.js b/packages/stylesheet/src/expand/index.js index 5d61c848f..fc056ab00 100644 --- a/packages/stylesheet/src/expand/index.js +++ b/packages/stylesheet/src/expand/index.js @@ -49,9 +49,9 @@ const shorthands = { /** * Transforms style key-value * - * @param {String} key style key - * @param {String} value style value - * @returns {String | Number} transformed style values + * @param {string} key style key + * @param {string} value style value + * @returns {string | Number} transformed style values */ const expandStyle = (key, value) => { return shorthands[key] ? shorthands[key](key, value) : { [key]: value }; @@ -60,10 +60,10 @@ const expandStyle = (key, value) => { /** * Expand the shorthand properties. * - * @param { Object } style object - * @returns { Object } expanded style object + * @param {Object} style object + * @returns {Object} expanded style object */ -const expand = style => { +const expand = (style) => { if (!style) return style; const propsArray = Object.keys(style); diff --git a/packages/stylesheet/src/flatten/index.js b/packages/stylesheet/src/flatten/index.js index d70071d88..2889adf67 100644 --- a/packages/stylesheet/src/flatten/index.js +++ b/packages/stylesheet/src/flatten/index.js @@ -3,22 +3,23 @@ import { compose, castArray } from '@react-pdf/fns'; /** * Remove nil values from array * - * @param {Array} array - * @returns {Array} array without nils + * @template T + * @param {(T | null | undefined)[]} array + * @returns {T[]} array without nils */ -const compact = array => array.filter(Boolean); +const compact = (array) => array.filter(Boolean); /** * Merges style objects array * - * @param {Array} style objects array + * @param {Object[]} styles style objects array * @returns {Object} merged style object */ -const mergeStyles = styles => +const mergeStyles = (styles) => styles.reduce((acc, style) => { const s = Array.isArray(style) ? flatten(style) : style; - Object.keys(s).forEach(key => { + Object.keys(s).forEach((key) => { if (s[key] !== null && s[key] !== undefined) { acc[key] = s[key]; } @@ -30,8 +31,8 @@ const mergeStyles = styles => /** * Flattens an array of style objects, into one aggregated style object. * - * @param {Array} style objects array - * @returns {Object} flatted style object + * @param {Object[]} styles style objects array + * @returns {Object} flattened style object */ const flatten = compose(mergeStyles, compact, castArray); diff --git a/packages/stylesheet/src/transform/colors.js b/packages/stylesheet/src/transform/colors.js index bd437c35b..978cf9567 100644 --- a/packages/stylesheet/src/transform/colors.js +++ b/packages/stylesheet/src/transform/colors.js @@ -7,7 +7,7 @@ const isHsl = value => /hsla?/g.test(value); /** * Transform rgb color to hexa * - * @param {String} styles value + * @param {string} value styles value * @returns {Object} transformed value */ const parseRgb = value => { @@ -18,7 +18,7 @@ const parseRgb = value => { /** * Transform Hsl color to hexa * - * @param {String} styles value + * @param {string} value styles value * @returns {Object} transformed value */ const parseHsl = value => { @@ -31,7 +31,7 @@ const parseHsl = value => { /** * Transform given color to hexa * - * @param {String} styles value + * @param {string} value styles value * @returns {Object} transformed value */ const transformColor = value => { diff --git a/packages/stylesheet/src/transform/index.js b/packages/stylesheet/src/transform/index.js index 9091a1ec4..972d3eb34 100644 --- a/packages/stylesheet/src/transform/index.js +++ b/packages/stylesheet/src/transform/index.js @@ -21,13 +21,19 @@ const transformStyle = (key, value, container) => { return transformColor(transformUnits(container, castFloat(result))); }; +/** + * @typedef {Function} Transform + * @param {Object} style styles object + * @returns {Object} transformed styles + */ + /** * Transform styles values * - * @param {Object} styles object - * @returns {Object} transformed styles + * @param {Object} container + * @returns {Transform} transform function */ -const transform = container => style => { +const transform = (container) => (style) => { if (!style) return style; const propsArray = Object.keys(style); diff --git a/packages/stylesheet/src/transform/units.js b/packages/stylesheet/src/transform/units.js index bc235a332..5854ba3d5 100644 --- a/packages/stylesheet/src/transform/units.js +++ b/packages/stylesheet/src/transform/units.js @@ -1,14 +1,14 @@ /** * Parses scalar value in value and unit pairs * - * @param {String} scalar value + * @param {string} value scalar value * @returns {Object} parsed value */ const parseValue = value => { const match = /^(-?\d*\.?\d+)(in|mm|cm|pt|vh|vw|px)?$/g.exec(value); return match - ? { value: parseFloat(match[1], 10), unit: match[2] || 'pt' } + ? { value: parseFloat(match[1]), unit: match[2] || 'pt' } : { value, unit: undefined }; }; @@ -16,7 +16,7 @@ const parseValue = value => { * Transform given scalar value * * @param {Object} container - * @param {String} styles value + * @param {string} value styles value * @returns {Object} transformed value */ const transformUnit = (container, value) => { diff --git a/packages/stylesheet/src/utils/castFloat.js b/packages/stylesheet/src/utils/castFloat.js index 992b9f494..3f7c5a824 100644 --- a/packages/stylesheet/src/utils/castFloat.js +++ b/packages/stylesheet/src/utils/castFloat.js @@ -1,9 +1,9 @@ -const matchNumber = value => +const matchNumber = (value) => typeof value === 'string' && /^-?\d*\.?\d*$/.test(value); -const castFloat = value => { +const castFloat = (value) => { if (typeof value !== 'string') return value; - if (matchNumber(value)) return parseFloat(value, 10); + if (matchNumber(value)) return parseFloat(value); return value; }; diff --git a/packages/stylesheet/tests/resolve.test.js b/packages/stylesheet/tests/resolve.test.js index d2cfaed5b..2eef3663b 100644 --- a/packages/stylesheet/tests/resolve.test.js +++ b/packages/stylesheet/tests/resolve.test.js @@ -19,7 +19,7 @@ describe('stylesheet resolve', () => { const style = {}; const result = resolve({}, style); - expect(result).toEqual({}, {}); + expect(result).toEqual({}); }); test('should return identity for single style object', () => { diff --git a/packages/svgkit/src/document/index.js b/packages/svgkit/src/document/index.js index 6f7bce28f..a6d0e15a9 100644 --- a/packages/svgkit/src/document/index.js +++ b/packages/svgkit/src/document/index.js @@ -9,10 +9,22 @@ import serialize from './serialize'; import { LinearGradient, RadialGradient } from '../gradient'; class SVGDocument { + /** + * @param {{ font?: Object }} [options] + */ constructor({ font } = {}) { this.info = {}; + /** + * @type {Object[]} + */ this.pages = []; + /** + * @type {Object} + */ this.currentPage = null; + /** + * @type {Object} + */ this.defaultFont = font; } @@ -268,7 +280,7 @@ class SVGDocument { } end() { - this.serialized = this.pages.map(page => serialize(page.root)).join(''); + this.serialized = this.pages.map((page) => serialize(page.root)).join(''); } } diff --git a/packages/svgkit/src/page/index.js b/packages/svgkit/src/page/index.js index 600af8e1f..6c4bff368 100644 --- a/packages/svgkit/src/page/index.js +++ b/packages/svgkit/src/page/index.js @@ -76,9 +76,18 @@ class SVGPage { const state = this.stack.pop(); this.applyStyleState(state); } + + // eslint-disable-next-line class-methods-use-this + setDefaultStyles() {} + + // eslint-disable-next-line class-methods-use-this, no-unused-vars + applyStyleState(state) {} + + // eslint-disable-next-line class-methods-use-this + getStyleState() {} } -const mixin = methods => { +const mixin = (methods) => { return (() => { const result = []; for (const name in methods) { diff --git a/packages/svgkit/src/utils/getPageSize.js b/packages/svgkit/src/utils/getPageSize.js index d373091ee..6b387771b 100644 --- a/packages/svgkit/src/utils/getPageSize.js +++ b/packages/svgkit/src/utils/getPageSize.js @@ -55,53 +55,59 @@ const PAGE_SIZES = { /** * Transforms array into size object * - * @param {Array} array - * @returns {Object} size object with width and height + * @param {number[]} v array + * @returns {{ width: number, height: number }} size object with width and height */ -const toSizeObject = v => ({ width: v[0], height: v[1] }); +const toSizeObject = (v) => ({ width: v[0], height: v[1] }); /** * Flip size object * - * @param {Object} size object - * @returns {Object} flipped size object + * @param {{ width: number, height: number }} v size object + * @returns {{ width: number, height: number }} flipped size object */ -const flipSizeObject = v => ({ width: v.height, height: v.width }); +const flipSizeObject = (v) => ({ width: v.height, height: v.width }); /** * Returns size object from a given string * - * @param {String} page size string - * @returns {Object} size object with width and height + * @param {string} v page size string + * @returns {{ width: number, height: number }} size object with width and height */ -const getStringSize = v => { +const getStringSize = (v) => { return toSizeObject(PAGE_SIZES[v.toUpperCase()]); }; /** * Returns size object from a single number * - * @param {Number} page size number - * @returns {Object} size object with width and height + * @param {number} n page size number + * @returns {{ width: number, height: number }} size object with width and height */ -const getNumberSize = n => toSizeObject([n]); +const getNumberSize = (n) => toSizeObject([n]); /** - * // TODO: Move this to separate pacjage to reuse with layout + * // TODO: Move this to separate package to reuse with layout * Return page size in an object { width, height } * - * @param {Object} page instance - * @returns {Object} size object with width and height + * @param {string | number[] | number | { width: number, height: number }} value page instance + * @param {string} orientation page orientation + * @returns {{ width: number, height: number }} size object with width and height */ const getSize = (value, orientation) => { - let size = value; + /** + * @type {{ width: number, height: number }} + */ + let size; - if (typeof size === 'string') { + if (typeof value === 'string') { size = getStringSize(value); } else if (Array.isArray(value)) { size = toSizeObject(value); - } else if (typeof size === 'number') { + } else if (typeof value === 'number') { size = getNumberSize(value); + } else { + size = value; } return orientation === 'landscape' ? flipSizeObject(size) : size; diff --git a/packages/textkit/src/attributedString/advanceWidth.js b/packages/textkit/src/attributedString/advanceWidth.js index 4f4075bc9..05f536978 100644 --- a/packages/textkit/src/attributedString/advanceWidth.js +++ b/packages/textkit/src/attributedString/advanceWidth.js @@ -3,12 +3,12 @@ import runAdvanceWidth from '../run/advanceWidth'; /** * Returns attributed string advancewidth * - * @param {Object} attributed string - * @return {number} advance width + * @param {Object} attributedString attributed string + * @returns {number} advance width */ -const advanceWidth = attributeString => { +const advanceWidth = attributedString => { const reducer = (acc, run) => acc + runAdvanceWidth(run); - return attributeString.runs.reduce(reducer, 0); + return attributedString.runs.reduce(reducer, 0); }; export default advanceWidth; diff --git a/packages/textkit/src/attributedString/advanceWidthBetween.js b/packages/textkit/src/attributedString/advanceWidthBetween.js index a44ca9edc..675b7195a 100644 --- a/packages/textkit/src/attributedString/advanceWidthBetween.js +++ b/packages/textkit/src/attributedString/advanceWidthBetween.js @@ -6,10 +6,10 @@ import runAdvanceWidthBetween from '../run/advanceWidthBetween'; * Does not consider ligature splitting for the moment. * Check performance impact on supporting this * - * @param {number} start offset - * @param {number} end offset - * @param {Object} attributedString - * @return {number} advance width + * @param {number} start offset + * @param {number} end offset + * @param {Object} attributedString + * @returns {number} advance width */ const advanceWidthBetween = (start, end, attributedString) => { const runs = filterRuns(start, end, attributedString.runs); diff --git a/packages/textkit/src/attributedString/append.js b/packages/textkit/src/attributedString/append.js index 99203f282..c259a9e13 100644 --- a/packages/textkit/src/attributedString/append.js +++ b/packages/textkit/src/attributedString/append.js @@ -8,8 +8,8 @@ import stringFromCodePoints from '../utils/stringFromCodePoints'; * Append glyph into last run of attributed string * * @param {Object} glyph - * @param {Object} attributed string - * @return {Object} attributed string with new glyph + * @param {Object} attributedString attributed string + * @returns {Object} attributed string with new glyph */ const append = (glyph, attributedString) => { const codePoints = glyph?.codePoints || []; diff --git a/packages/textkit/src/attributedString/ascent.js b/packages/textkit/src/attributedString/ascent.js index bdf444a0d..ce8cc7e8a 100644 --- a/packages/textkit/src/attributedString/ascent.js +++ b/packages/textkit/src/attributedString/ascent.js @@ -3,12 +3,12 @@ import runAscent from '../run/ascent'; /** * Returns attributed string ascent * - * @param {Object} attributed string - * @return {number} ascent + * @param {Object} attributedString attributed string + * @returns {number} ascent */ -const ascent = attributeString => { +const ascent = attributedString => { const reducer = (acc, run) => Math.max(acc, runAscent(run)); - return attributeString.runs.reduce(reducer, 0); + return attributedString.runs.reduce(reducer, 0); }; export default ascent; diff --git a/packages/textkit/src/attributedString/descent.js b/packages/textkit/src/attributedString/descent.js index bc7c254f1..d9d6a696f 100644 --- a/packages/textkit/src/attributedString/descent.js +++ b/packages/textkit/src/attributedString/descent.js @@ -3,12 +3,12 @@ import runDescent from '../run/descent'; /** * Returns attributed string descent * - * @param {Object} attributed string - * @return {number} descent + * @param {Object} attributedString attributed string + * @returns {number} descent */ -const descent = attributeString => { +const descent = attributedString => { const reducer = (acc, run) => Math.min(acc, runDescent(run)); - return attributeString.runs.reduce(reducer, 0); + return attributedString.runs.reduce(reducer, 0); }; export default descent; diff --git a/packages/textkit/src/attributedString/dropLast.js b/packages/textkit/src/attributedString/dropLast.js index a94beab7f..090054a61 100644 --- a/packages/textkit/src/attributedString/dropLast.js +++ b/packages/textkit/src/attributedString/dropLast.js @@ -5,14 +5,14 @@ import runDropLast from '../run/dropLast'; /** * Drop last glyph * - * @param {Object} attributed string - * @return {Object} attributed string with new glyph + * @param {Object} attributedString attributed string + * @returns {Object} attributed string with new glyph */ -const dropLast = attributeString => { - const string = arrayDropLast(attributeString.string); - const runs = adjust(-1, runDropLast, attributeString.runs); +const dropLast = attributedString => { + const string = arrayDropLast(attributedString.string); + const runs = adjust(-1, runDropLast, attributedString.runs); - return Object.assign({}, attributeString, { string, runs }); + return Object.assign({}, attributedString, { string, runs }); }; export default dropLast; diff --git a/packages/textkit/src/attributedString/empty.js b/packages/textkit/src/attributedString/empty.js index cc48b1a48..b903326e9 100644 --- a/packages/textkit/src/attributedString/empty.js +++ b/packages/textkit/src/attributedString/empty.js @@ -1,7 +1,7 @@ /** * Returns empty attributed string * - * @return {Object} empty attributed string + * @returns {Object} empty attributed string */ const empty = () => ({ string: '', runs: [] }); diff --git a/packages/textkit/src/attributedString/end.js b/packages/textkit/src/attributedString/end.js index d02d571fc..49e801b5d 100644 --- a/packages/textkit/src/attributedString/end.js +++ b/packages/textkit/src/attributedString/end.js @@ -3,8 +3,8 @@ import { last } from '@react-pdf/fns'; /** * Get attributed string end value * - * @param {Object} attributed string - * @return {number} end + * @param {Object} attributedString attributed string + * @returns {number} end */ const end = attributedString => { const { runs } = attributedString; diff --git a/packages/textkit/src/attributedString/fromFragments.js b/packages/textkit/src/attributedString/fromFragments.js index cca715ebe..501819928 100644 --- a/packages/textkit/src/attributedString/fromFragments.js +++ b/packages/textkit/src/attributedString/fromFragments.js @@ -1,15 +1,15 @@ /** * Create attributed string from text fragments * - * @param {Array} fragments - * @return {Object} attributed string + * @param {Object[]} fragments fragments + * @returns {Object} attributed string */ -const fromFragments = fragments => { +const fromFragments = (fragments) => { let offset = 0; let string = ''; const runs = []; - fragments.forEach(fragment => { + fragments.forEach((fragment) => { string += fragment.string; runs.push({ diff --git a/packages/textkit/src/attributedString/glyphWidthAt.js b/packages/textkit/src/attributedString/glyphWidthAt.js index c8777de8d..02ab808c1 100644 --- a/packages/textkit/src/attributedString/glyphWidthAt.js +++ b/packages/textkit/src/attributedString/glyphWidthAt.js @@ -4,9 +4,9 @@ import glyphIndexAt from '../run/glyphIndexAt'; /** * Get glyph width at string index * - * @param {number} string index - * @param {Object} attributed string - * @return {number} glyph width + * @param {number} index string index + * @param {Object} string attributed string + * @returns {number} glyph width */ const glyphWidthAt = (index, string) => { const run = runAt(index, string); diff --git a/packages/textkit/src/attributedString/height.js b/packages/textkit/src/attributedString/height.js index 6e7a86684..3668eb990 100644 --- a/packages/textkit/src/attributedString/height.js +++ b/packages/textkit/src/attributedString/height.js @@ -3,12 +3,12 @@ import runHeight from '../run/height'; /** * Returns attributed string height * - * @param {Object} attributed string - * @return {number} height + * @param {Object} attributedString attributed string + * @returns {number} height */ -const height = attributeString => { +const height = attributedString => { const reducer = (acc, run) => Math.max(acc, runHeight(run)); - return attributeString.runs.reduce(reducer, 0); + return attributedString.runs.reduce(reducer, 0); }; export default height; diff --git a/packages/textkit/src/attributedString/indexAtOffset.js b/packages/textkit/src/attributedString/indexAtOffset.js index 2c394c255..34b3fd733 100644 --- a/packages/textkit/src/attributedString/indexAtOffset.js +++ b/packages/textkit/src/attributedString/indexAtOffset.js @@ -5,9 +5,9 @@ import runIndexAtOffset from '../run/indexAtOffset'; /** * Get string index at offset * - * @param {Object} attributed string - * @param {number} offset - * @return {number} string index at offset N + * @param {number} offset offset + * @param {Object} string attributed string + * @returns {number} string index at offset N */ const indexAtOffset = (offset, string) => { let index = 0; diff --git a/packages/textkit/src/attributedString/insertGlyph.js b/packages/textkit/src/attributedString/insertGlyph.js index 43537a7f4..36264a1f9 100644 --- a/packages/textkit/src/attributedString/insertGlyph.js +++ b/packages/textkit/src/attributedString/insertGlyph.js @@ -9,8 +9,8 @@ import stringFromCodePoints from '../utils/stringFromCodePoints'; * * @param {number} index * @param {Object} glyph - * @param {Object} attributed string - * @return {Object} attributed string with new glyph + * @param {Object} attributedString attributed string + * @returns {Object} attributed string with new glyph */ const insertGlyph = (index, glyph, attributedString) => { const runIndex = runIndexAt(index, attributedString); diff --git a/packages/textkit/src/attributedString/leadingOffset.js b/packages/textkit/src/attributedString/leadingOffset.js index 44b7bdb97..331c36bf9 100644 --- a/packages/textkit/src/attributedString/leadingOffset.js +++ b/packages/textkit/src/attributedString/leadingOffset.js @@ -3,8 +3,8 @@ import runLeadingOffset from '../run/leadingOffset'; /** * Get attributed string leading white space offset * - * @param {Object} attributed string - * @return {number} leading white space offset + * @param {Object} attributedString attributed string + * @returns {number} leading white space offset */ const leadingOffset = attributedString => { const runs = attributedString.runs || []; diff --git a/packages/textkit/src/attributedString/length.js b/packages/textkit/src/attributedString/length.js index 6074a317c..b323e9d63 100644 --- a/packages/textkit/src/attributedString/length.js +++ b/packages/textkit/src/attributedString/length.js @@ -4,8 +4,8 @@ import end from './end'; /** * Get attributed string length * - * @param {Object} glyph string - * @return {number} end + * @param {Object} attributedString glyph string + * @returns {number} end */ const length = attributedString => { return end(attributedString) - start(attributedString); diff --git a/packages/textkit/src/attributedString/prepend.js b/packages/textkit/src/attributedString/prepend.js index bc3305770..080b9ff9b 100644 --- a/packages/textkit/src/attributedString/prepend.js +++ b/packages/textkit/src/attributedString/prepend.js @@ -7,8 +7,8 @@ import stringFromCodePoints from '../utils/stringFromCodePoints'; * prepend glyph into last run of attributed string * * @param {Object} glyph - * @param {Object} attributed string - * @return {Object} attributed string with new glyph + * @param {Object} attributedString attributed string + * @returns {Object} attributed string with new glyph */ const prepend = (glyph, attributedString) => { const codePoints = glyph?.codePoints || []; diff --git a/packages/textkit/src/attributedString/runAt.js b/packages/textkit/src/attributedString/runAt.js index 57670e9ee..c15303173 100644 --- a/packages/textkit/src/attributedString/runAt.js +++ b/packages/textkit/src/attributedString/runAt.js @@ -3,9 +3,9 @@ import runIndexAt from './runIndexAt'; /** * Get run at char index * - * @param {number} char index - * @param {Object} attributedString - * @return {Object} run + * @param {number} n char index + * @param {Object} attributedString attributed string + * @returns {Object} run */ const runAt = (n, attributedString) => { const runIndex = runIndexAt(n, attributedString); diff --git a/packages/textkit/src/attributedString/runIndexAt.js b/packages/textkit/src/attributedString/runIndexAt.js index 1a8adfa10..cb1457788 100644 --- a/packages/textkit/src/attributedString/runIndexAt.js +++ b/packages/textkit/src/attributedString/runIndexAt.js @@ -3,9 +3,9 @@ import runIndexAtInternal from '../run/runIndexAt'; /** * Get run index at char index * - * @param {number} char index - * @param {Object} attributedString - * @return {number} run index + * @param {number} n char index + * @param {Object} string attributed string + * @returns {number} run index */ const runIndexAt = (n, string) => { return runIndexAtInternal(n, string.runs); diff --git a/packages/textkit/src/attributedString/slice.js b/packages/textkit/src/attributedString/slice.js index 518e4ea7a..ad17c8ea1 100644 --- a/packages/textkit/src/attributedString/slice.js +++ b/packages/textkit/src/attributedString/slice.js @@ -5,14 +5,14 @@ import subtractRun from '../run/subtract'; /** * Slice array of runs * - * @param {number} start offset - * @param {number} end offset - * @param {Array} runs - * @return {Array} sliced runs + * @param {number} start offset + * @param {number} end offset + * @param {Object[]} runs + * @returns {Object[]} sliced runs */ const sliceRuns = (start, end, runs) => { - const sliceFirstRun = a => sliceRun(start - a.start, end - a.start, a); - const sliceLastRun = a => sliceRun(0, end - a.start, a); + const sliceFirstRun = (a) => sliceRun(start - a.start, end - a.start, a); + const sliceLastRun = (a) => sliceRun(0, end - a.start, a); return runs.map((run, i) => { let result = run; @@ -30,10 +30,10 @@ const sliceRuns = (start, end, runs) => { /** * Slice attributed string between two indices * - * @param {number} start offset - * @param {number} end offset - * @param {Object} attributedString - * @return {Object} attributedString + * @param {number} start offset + * @param {number} end offset + * @param {Object} attributedString attributed string + * @returns {Object} attributedString */ const slice = (start, end, attributedString) => { if (attributedString.string.length === 0) return attributedString; diff --git a/packages/textkit/src/attributedString/sliceAtOffset.js b/packages/textkit/src/attributedString/sliceAtOffset.js index f35362e15..3e6a86632 100644 --- a/packages/textkit/src/attributedString/sliceAtOffset.js +++ b/packages/textkit/src/attributedString/sliceAtOffset.js @@ -4,9 +4,9 @@ import indexAtOffset from './indexAtOffset'; /** * Slice attributed string at given offset * - * @param {number} offset - * @param {Object} attributedString - * @return {Object} attributedString + * @param {number} offset offset + * @param {Object} string attributedString + * @returns {Object} attributedString */ const sliceAtOffset = (offset, string) => { const index = indexAtOffset(offset, string); diff --git a/packages/textkit/src/attributedString/start.js b/packages/textkit/src/attributedString/start.js index 927441d3b..bb20a4ad3 100644 --- a/packages/textkit/src/attributedString/start.js +++ b/packages/textkit/src/attributedString/start.js @@ -1,8 +1,8 @@ /** * Get attributed string start value * - * @param {Object} attributed string - * @return {number} start + * @param {Object} attributedString attributed string + * @returns {number} start */ const start = attributedString => { const { runs } = attributedString; diff --git a/packages/textkit/src/attributedString/trailingOffset.js b/packages/textkit/src/attributedString/trailingOffset.js index 2f55d6bb0..85ea92e08 100644 --- a/packages/textkit/src/attributedString/trailingOffset.js +++ b/packages/textkit/src/attributedString/trailingOffset.js @@ -5,8 +5,8 @@ import runTrailingOffset from '../run/trailingOffset'; /** * Get attributed string trailing white space offset * - * @param {Object} attributed string - * @return {number} trailing white space offset + * @param {Object} attributedString attributed string + * @returns {number} trailing white space offset */ const trailingOffset = attributedString => { const runs = attributedString.runs || []; diff --git a/packages/textkit/src/attributedString/trim.js b/packages/textkit/src/attributedString/trim.js index b000c5b69..1a9c3e3f9 100644 --- a/packages/textkit/src/attributedString/trim.js +++ b/packages/textkit/src/attributedString/trim.js @@ -10,8 +10,8 @@ const findLastCharIndex = string => { /** * Removes (strips) whitespace from both ends of the attributted string. * - * @param {Object} attributedString - * @return {Object} attributedString + * @param {Object} attributedString + * @returns {Object} attributedString */ const trim = attributedString => { const start = findCharIndex(attributedString.string); diff --git a/packages/textkit/src/block/height.js b/packages/textkit/src/block/height.js index 8937f7a4d..bf8a62e08 100644 --- a/packages/textkit/src/block/height.js +++ b/packages/textkit/src/block/height.js @@ -1,8 +1,8 @@ /** * Get paragraph block height * - * @param {Object} paragraph block - * @return {number} paragraph block height + * @param {Object} paragraph block + * @returns {number} paragraph block height */ const height = paragraph => { return paragraph.reduce((acc, block) => acc + block.box.height, 0); diff --git a/packages/textkit/src/block/sliceAtHeight.js b/packages/textkit/src/block/sliceAtHeight.js index e231897d3..786be6472 100644 --- a/packages/textkit/src/block/sliceAtHeight.js +++ b/packages/textkit/src/block/sliceAtHeight.js @@ -1,9 +1,9 @@ /** * Slice block at given height * - * @param {number} height - * @param {Object} paragraph block - * @return {number} sliced paragraph block + * @param {number} height height + * @param {Object} block paragraph block + * @returns {number[]} sliced paragraph block */ const sliceAtHeight = (height, block) => { const newBlock = []; diff --git a/packages/textkit/src/block/truncate.js b/packages/textkit/src/block/truncate.js index 02bc67590..d029f80f2 100644 --- a/packages/textkit/src/block/truncate.js +++ b/packages/textkit/src/block/truncate.js @@ -9,8 +9,8 @@ const ELLIPSIS_STRING = String.fromCharCode(ELLIPSIS_UNICODE); /** * Get ellipsis codepoint. This may be different in standard and embedded fonts * - * @param {number} font - * @return {Object} ellipsis codepoint + * @param {Object} font + * @returns {Object} ellipsis codepoint */ const getEllipsisCodePoint = font => { if (!font.encode) return ELLIPSIS_UNICODE; @@ -23,9 +23,8 @@ const getEllipsisCodePoint = font => { /** * Trucante block with ellipsis * - * @param {number} lines quantity - * @param {Object} paragraph block - * @return {Object} sliced paragraph block + * @param {Object} block paragraph block + * @returns {Object} sliced paragraph block */ const truncate = block => { const runs = last(block)?.runs || []; diff --git a/packages/textkit/src/engines/fontSubstitution/index.js b/packages/textkit/src/engines/fontSubstitution/index.js index 1ebd863ae..56cffd617 100644 --- a/packages/textkit/src/engines/fontSubstitution/index.js +++ b/packages/textkit/src/engines/fontSubstitution/index.js @@ -6,13 +6,17 @@ import empty from '../../attributedString/empty'; const getFontSize = value => value.attributes.fontSize || 12; +/** + * @typedef {Function} FontSubstitution + * @param {Object} attributedString attributed string + * @returns {Object} attributed string + */ + /** * Resolve font runs in an AttributedString, grouping equal * runs and performing font substitution where necessary. * - * @param {Object} layout options - * @param {Object} attributed string - * @return {Object} attributed string + * @returns {FontSubstitution} font substitution */ const fontSubstitution = () => attributedString => { const { string, runs } = attributedString; diff --git a/packages/textkit/src/engines/justification/index.js b/packages/textkit/src/engines/justification/index.js index 33164f78b..fb62b8bfd 100644 --- a/packages/textkit/src/engines/justification/index.js +++ b/packages/textkit/src/engines/justification/index.js @@ -9,7 +9,7 @@ import advanceWidth from '../../attributedString/advanceWidth'; /** * Adjust run positions by given distances * - * @param {Array} distances + * @param {number[]} distances * @param {Object} line * @returns {Object} line */ @@ -24,18 +24,23 @@ const justifyLine = (distances, line) => { return line; }; +/** + * @typedef {Function} Justification + * @param {Object} line + * @returns {Object} line + */ + /** * A JustificationEngine is used by a Typesetter to perform line fragment * justification. This implementation is based on a description of Apple's * justification algorithm from a PDF in the Apple Font Tools package. * - * //TODO: Make it immutable + * // TODO: Make it immutable * - * @param {Object} layout options - * @param {Object} line - * @returns {Object} line + * @param {Object} options layout options + * @returns {Justification} justification engine */ -const justification = options => line => { +const justification = (options) => (line) => { const gap = line.box.width - advanceWidth(line); if (gap === 0) return; // Exact fit diff --git a/packages/textkit/src/engines/linebreaker/index.js b/packages/textkit/src/engines/linebreaker/index.js index 6f1d67b75..fb0cd60c7 100644 --- a/packages/textkit/src/engines/linebreaker/index.js +++ b/packages/textkit/src/engines/linebreaker/index.js @@ -17,10 +17,10 @@ const opts = { /** * Slice attributed string to many lines * - * @param {Object} attributed string - * @param {Array} nodes - * @param {Array} breaks - * @return {Array} attributed strings + * @param {Object} string attributed string + * @param {Object[]} nodes + * @param {Object[]} breaks + * @returns {Object[]} attributed strings */ const breakLines = (string, nodes, breaks) => { let start = 0; @@ -57,10 +57,10 @@ const breakLines = (string, nodes, breaks) => { /** * Return Knuth & Plass nodes based on line and previously calculated syllables * - * @param {Object} attributed string - * @param {Object} attributed string - * @param {Object} layout options - * @return {Array} attributed strings + * @param {Object} attributedString attributed string + * @param {Object} args attributed string args + * @param {Object} options layout options + * @returns {Object[]} attributed strings */ const getNodes = (attributedString, { align }, options) => { let start = 0; @@ -105,24 +105,30 @@ const getNodes = (attributedString, { align }, options) => { return result; }; -const getStyles = attributedString => +const getStyles = (attributedString) => attributedString.runs?.[0]?.attributes || {}; +/** + * @typedef {Function} LineBreaker + * @param {Object} attributedString attributed string + * @param {Object} availableWidths available widths + * @returns {Object[]} attributed strings + */ + /** * Performs Knuth & Plass line breaking algorithm * Fallbacks to best fit algorithm if latter not successful * - * @param {Object} layout options - * @param {Object} attributed string - * @param {Object} attributed string - * @return {Array} attributed strings + * @param {Object} options layout options + * @returns {LineBreaker} line breaker */ -const linebreaker = options => (attributedString, availableWidths) => { +const linebreaker = (options) => (attributedString, availableWidths) => { let tolerance = options.tolerance || 4; const style = getStyles(attributedString); const nodes = getNodes(attributedString, style, options); + /** @type {Object[]} */ let breaks = linebreak(nodes, availableWidths, { tolerance }); // Try again with a higher tolerance if the line breaking failed. diff --git a/packages/textkit/src/engines/linebreaker/linebreak.js b/packages/textkit/src/engines/linebreaker/linebreak.js index f6b0edfd7..16277990b 100644 --- a/packages/textkit/src/engines/linebreaker/linebreak.js +++ b/packages/textkit/src/engines/linebreaker/linebreak.js @@ -131,12 +131,18 @@ const linebreak = (nodes, lines, settings) => { let next = null; let ratio = 0; let demerits = 0; + /** + * @type {Object[]} + */ let candidates = []; let badness; let currentLine = 0; let tmpSum; let currentClass = 0; let fitnessClass; + /** + * @type {Object} + */ let candidate; let newNode; diff --git a/packages/textkit/src/engines/linebreaker/linkedList.js b/packages/textkit/src/engines/linebreaker/linkedList.js index c069d4828..f1ca27a35 100644 --- a/packages/textkit/src/engines/linebreaker/linkedList.js +++ b/packages/textkit/src/engines/linebreaker/linkedList.js @@ -19,6 +19,7 @@ class LinkedList { this.head = null; this.tail = null; this.listSize = 0; + this.listLength = 0; } isLinked(node) { diff --git a/packages/textkit/src/engines/scriptItemizer/index.js b/packages/textkit/src/engines/scriptItemizer/index.js index b7575dde8..b171a9ee3 100644 --- a/packages/textkit/src/engines/scriptItemizer/index.js +++ b/packages/textkit/src/engines/scriptItemizer/index.js @@ -4,12 +4,16 @@ import empty from '../../attributedString/empty'; const ignoredScripts = ['Common', 'Inherited', 'Unknown']; +/** + * @typedef {Function} ScriptItemizer + * @param {Object} attributedString attributed string + * @returns {Object} attributed string + */ + /** * Resolves unicode script in runs, grouping equal runs together * - * @param {Object} layout options - * @param {Object} attributed string - * @return {Object} attributed string + * @returns {ScriptItemizer} script itemizer */ const scriptItemizer = () => attributedString => { const { string } = attributedString; diff --git a/packages/textkit/src/glyph/fromCodePoint.js b/packages/textkit/src/glyph/fromCodePoint.js index 66389ef4a..ac1302986 100644 --- a/packages/textkit/src/glyph/fromCodePoint.js +++ b/packages/textkit/src/glyph/fromCodePoint.js @@ -1,9 +1,9 @@ /** * Get glyph for a given code point * - * @param {number} codePoint - * @param {Object} font - * @return {Object} glyph + * @param {number} [value] codePoint + * @param {Object} [font] font + * @returns {Object} glyph * */ const fromCodePoint = (value, font) => font && value ? font.glyphForCodePoint(value) : null; diff --git a/packages/textkit/src/glyph/isWhiteSpace.js b/packages/textkit/src/glyph/isWhiteSpace.js index 0d601679f..7a91d207a 100644 --- a/packages/textkit/src/glyph/isWhiteSpace.js +++ b/packages/textkit/src/glyph/isWhiteSpace.js @@ -3,10 +3,10 @@ const WHITE_SPACES_CODE = 32; /** * Check if glyph is white space * - * @param {Object} glyph - * @return {Boolean} is white space + * @param {Object} glyph + * @returns {boolean} is white space * */ -const isWhiteSpace = glyph => { +const isWhiteSpace = (glyph) => { const codePoints = glyph?.codePoints || []; return codePoints.includes(WHITE_SPACES_CODE); }; diff --git a/packages/textkit/src/glyph/slice.js b/packages/textkit/src/glyph/slice.js index 220c60403..fd1173559 100644 --- a/packages/textkit/src/glyph/slice.js +++ b/packages/textkit/src/glyph/slice.js @@ -2,11 +2,11 @@ * Slice glyph between codePoints range * Util for breaking ligatures * - * @param {number} start code point index - * @param {number} end code point index - * @param {Object} font to generate new glyph - * @param {Object} glyph to be sliced - * @return {Array} sliced glyph parts + * @param {number} start code point index + * @param {number} end code point index + * @param {Object} font to generate new glyph + * @param {Object} glyph to be sliced + * @returns {Object[]} sliced glyph parts */ const slice = (start, end, font, glyph) => { if (!glyph) return []; diff --git a/packages/textkit/src/indices/append.js b/packages/textkit/src/indices/append.js index 04d114c53..a87dd7108 100644 --- a/packages/textkit/src/indices/append.js +++ b/packages/textkit/src/indices/append.js @@ -5,9 +5,9 @@ import { isNil, last } from '@react-pdf/fns'; * * Ex. appendIndices(3, [0, 1, 2, 2]) => [0, 1, 2, 2, 3, 3, 3] * - * @param {number} length - * @param {Array} glyph indices - * @return {Array} extended glyph indices + * @param {number} length length + * @param {number[]} indices glyph indices + * @returns {number[]} extended glyph indices */ const appendIndices = (length, indices) => { const lastIndex = last(indices); diff --git a/packages/textkit/src/indices/normalize.js b/packages/textkit/src/indices/normalize.js index 3b0baa639..3ba77ff88 100644 --- a/packages/textkit/src/indices/normalize.js +++ b/packages/textkit/src/indices/normalize.js @@ -1,8 +1,8 @@ /** * Returns new array starting with zero, and keeping same relation between consecutive values * - * @param {Array[number]} list - * @return {boolean} normalized array + * @param {number[]} array list + * @returns {number[]} normalized array */ const normalize = array => { const head = array[0]; diff --git a/packages/textkit/src/indices/prepend.js b/packages/textkit/src/indices/prepend.js index fbe189e30..a0cd7a3aa 100644 --- a/packages/textkit/src/indices/prepend.js +++ b/packages/textkit/src/indices/prepend.js @@ -3,15 +3,15 @@ * * Ex. prepend(3, [0, 1, 2, 2]) => [0, 0, 0, 1, 2, 3, 3] * - * @param {number} length - * @param {Array} glyph indices - * @return {Array} extended glyph indices + * @param {number} length length + * @param {number[]} indices glyph indices + * @returns {number[]} extended glyph indices */ const prepend = (length, indices) => { if (length === 0) return indices; const newIndices = Array(length).fill(0); - const lastIndices = indices.map(value => value + 1); + const lastIndices = indices.map((value) => value + 1); return newIndices.concat(lastIndices); }; diff --git a/packages/textkit/src/indices/resolve.js b/packages/textkit/src/indices/resolve.js index 87e2244be..579d7c6c4 100644 --- a/packages/textkit/src/indices/resolve.js +++ b/packages/textkit/src/indices/resolve.js @@ -1,10 +1,10 @@ -const DUMMY_CODEPOINT = 123 +const DUMMY_CODEPOINT = 123; /** * Resolve string indices based on glyphs code points * - * @param {Array} glyphs - * @return {Array} glyph indices + * @param {Object[]} glyphs + * @returns {number[]} glyph indices */ const resolve = (glyphs = []) => { return glyphs.reduce((acc, glyph) => { @@ -15,7 +15,7 @@ const resolve = (glyphs = []) => { const last = acc[acc.length - 1]; const next = codePoints.map(() => last + 1); - return [...acc, ...next] + return [...acc, ...next]; }, []); }; diff --git a/packages/textkit/src/layout/applyDefaultStyles.js b/packages/textkit/src/layout/applyDefaultStyles.js index b253e447d..f34080386 100644 --- a/packages/textkit/src/layout/applyDefaultStyles.js +++ b/packages/textkit/src/layout/applyDefaultStyles.js @@ -1,3 +1,7 @@ +/** + * @param {Object} a attributes + * @returns {Object} attributes with defaults + */ const applyAttributes = a => ({ align: a.align || 'left', alignLastLine: @@ -41,21 +45,24 @@ const applyAttributes = a => ({ /** * Apply default style to run * - * @param {Object} run - * @return {Object} run with styles + * @param {Object} run run + * @returns {Object} run with styles */ const applyRunStyles = run => { const attributes = applyAttributes(run.attributes); return Object.assign({}, run, { attributes }); }; +/** + * @typedef {Function} ApplyDefaultStyles + * @param {Object} attributedString attributed string + * @returns {Object} attributed string + */ + /** * Apply default attributes for an attributed string * - * @param {Object} engines - * @param {Object} layout options - * @param {Object} attributed string - * @return {Object} attributed string + * @returns {ApplyDefaultStyles} applyDefaultStyles */ const applyDefaultStyles = () => attributedString => { const string = attributedString.string || ''; diff --git a/packages/textkit/src/layout/finalizeFragments.js b/packages/textkit/src/layout/finalizeFragments.js index 462107128..deaeeb3e5 100644 --- a/packages/textkit/src/layout/finalizeFragments.js +++ b/packages/textkit/src/layout/finalizeFragments.js @@ -14,28 +14,28 @@ const ALIGNMENT_FACTORS = { center: 0.5, right: 1 }; /** * Remove new line char at the end of line if present * - * @param {Object} line - * @return {Object} line + * @param {Object} line + * @returns {Object} line */ -const removeNewLine = line => { +const removeNewLine = (line) => { return last(line.string) === '\n' ? dropLast(line) : line; }; -const getOverflowLeft = line => { +const getOverflowLeft = (line) => { return leadingOffset(line) + (line.overflowLeft || 0); }; -const getOverflowRight = line => { +const getOverflowRight = (line) => { return trailingOffset(line) + (line.overflowRight || 0); }; /** * Ignore whitespace at the start and end of a line for alignment * - * @param {Object} line - * @return {Object} line + * @param {Object} line + * @returns {Object} line */ -const adjustOverflow = line => { +const adjustOverflow = (line) => { const overflowLeft = getOverflowLeft(line); const overflowRight = getOverflowRight(line); @@ -46,16 +46,21 @@ const adjustOverflow = line => { return Object.assign({}, line, { box, overflowLeft, overflowRight }); }; +/** + * @typedef {Function} JustifyLine + * @param {Object} line + * @returns {Object} line + */ + /** * Performs line justification by calling appropiate engine * - * @param {Object} engines - * @param {Object} layout options - * @param {string} text align - * @param {Object} line - * @return {Object} line + * @param {Object} engines engines + * @param {Object} options layout options + * @param {string} align text align + * @returns {JustifyLine} justifyLine */ -const justifyLine = (engines, options, align) => line => { +const justifyLine = (engines, options, align) => (line) => { const lineWidth = advanceWidth(line); const alignFactor = ALIGNMENT_FACTORS[align] || 0; const remainingWidth = Math.max(0, line.box.width - lineWidth); @@ -68,13 +73,13 @@ const justifyLine = (engines, options, align) => line => { return shouldJustify ? engines.justification(options)(newLine) : newLine; }; -const finalizeLine = line => { +const finalizeLine = (line) => { let lineAscent = 0; let lineDescent = 0; let lineHeight = 0; let lineXAdvance = 0; - const runs = line.runs.map(run => { + const runs = line.runs.map((run) => { const height = runHeight(run); const ascent = runAscent(run); const descent = runDescent(run); @@ -97,43 +102,55 @@ const finalizeLine = line => { }); }; +/** + * @typedef {Function} FinalizeBlock + * @param {Object} line + * @param {number} i line index + * @param {Object[]} lines total lines + * @returns {Object} line + */ + /** * Finalize line by performing line justification * and text decoration (using appropiate engines) * - * @param {Object} engines - * @param {Object} layout options - * @param {Object} line - * @param {number} line index - * @param {Array} total lines - * @return {Object} line + * @param {Object} engines engines + * @param {Object} options layout options + * @returns {FinalizeBlock} finalize block + */ +const finalizeBlock = + (engines = {}, options) => + (line, i, lines) => { + const isLastFragment = i === lines.length - 1; + const style = line.runs?.[0]?.attributes || {}; + const align = isLastFragment ? style.alignLastLine : style.align; + + return compose( + finalizeLine, + engines.textDecoration(options), + justifyLine(engines, options, align), + adjustOverflow, + removeNewLine, + )(line); + }; + +/** + * @typedef {Function} FinalizeFragments + * @param {Object[]} blocks line blocks + * @returns {Object[]} blocks */ -const finalizeBlock = (engines = {}, options) => (line, i, lines) => { - const isLastFragment = i === lines.length - 1; - const style = line.runs?.[0]?.attributes || {}; - const align = isLastFragment ? style.alignLastLine : style.align; - - return compose( - finalizeLine, - engines.textDecoration(options), - justifyLine(engines, options, align), - adjustOverflow, - removeNewLine, - )(line); -}; /** * Finalize line block by performing line justification * and text decoration (using appropiate engines) * - * @param {Object} engines - * @param {Object} layout options - * @param {Array} line blocks - * @return {Array} line blocks + * @param {Object} engines engines + * @param {Object} options layout options + * @returns {FinalizeFragments} finalizeFragments */ -const finalizeFragments = (engines, options) => blocks => { +const finalizeFragments = (engines, options) => (blocks) => { const blockFinalizer = finalizeBlock(engines, options); - return blocks.map(block => block.map(blockFinalizer)); + return blocks.map((block) => block.map(blockFinalizer)); }; export default finalizeFragments; diff --git a/packages/textkit/src/layout/generateGlyphs.js b/packages/textkit/src/layout/generateGlyphs.js index 995b4869c..acadcd06c 100644 --- a/packages/textkit/src/layout/generateGlyphs.js +++ b/packages/textkit/src/layout/generateGlyphs.js @@ -1,14 +1,14 @@ import scale from '../run/scale'; import resolveGlyphIndices from '../indices/resolve'; -const getCharacterSpacing = run => run.attributes?.characterSpacing || 0; +const getCharacterSpacing = (run) => run.attributes?.characterSpacing || 0; /** * Scale run positions * - * @param {Object} run - * @param {Array} positions - * @return {Array} scaled positions + * @param {Object} run + * @param {Object[]} positions + * @returns {Object[]} scaled positions */ const scalePositions = (run, positions) => { const runScale = scale(run); @@ -27,14 +27,19 @@ const scalePositions = (run, positions) => { }); }; +/** + * @typedef {Function} LayoutRun + * @param {Object} run run + * @returns {Object} glyph run + */ + /** * Create glyph run * - * @param {String} string - * @param {Object} run - * @return {Object} glyph run + * @param {string} string string + * @returns {LayoutRun} layout run */ -const layoutRun = string => run => { +const layoutRun = (string) => (run) => { const { start, end, attributes = {} } = run; const { font } = attributes; @@ -53,15 +58,18 @@ const layoutRun = string => run => { }; }; +/** + * @typedef {Function} GenerateGlyphs + * @param {Object} attributedString attributed string + * @returns {Object} attributed string with glyphs + */ + /** * Generate glyphs for single attributed string * - * @param {Object} layout engines - * @param {Object} layout options - * @param {Array} attributed strings - * @return {Array} attributed string with glyphs + * @returns {GenerateGlyphs} generate glyphs */ -const generateGlyphs = () => attributedString => { +const generateGlyphs = () => (attributedString) => { const runs = attributedString.runs.map(layoutRun(attributedString.string)); return Object.assign({}, attributedString, { runs }); }; diff --git a/packages/textkit/src/layout/index.js b/packages/textkit/src/layout/index.js index 534917bca..272738366 100644 --- a/packages/textkit/src/layout/index.js +++ b/packages/textkit/src/layout/index.js @@ -11,6 +11,14 @@ import resolveAttachments from './resolveAttachments'; import applyDefaultStyles from './applyDefaultStyles'; import verticalAlignment from './verticalAlign'; +/** + * @typedef {Function} LayoutEngine + * @param {Object} attributedString attributed string + * @param {Object} container container rect + * @param {Object} options layout options + * @returns {Object[]} paragraph blocks + */ + /** * A LayoutEngine is the main object that performs text layout. * It accepts an AttributedString and a Container object @@ -18,18 +26,15 @@ import verticalAlignment from './verticalAlign'; * various layout tasks. These objects can be overridden to customize * layout behavior. * - * @param {Object} engines - * @param {Object} attributed string - * @param {Object} container rect - * @param {Object} layout options - * @return {Array} paragraph blocks + * @param {Object} engines engines + * @returns {LayoutEngine} layout engine */ const layoutEngine = engines => (attributedString, container, options = {}) => { const processParagraph = compose( - resolveYOffset(engines, options), - resolveAttachments(engines, options), - generateGlyphs(engines, options), - verticalAlignment(options), + resolveYOffset(), + resolveAttachments(), + generateGlyphs(), + verticalAlignment(), wrapWords(engines, options), ); @@ -39,9 +44,9 @@ const layoutEngine = engines => (attributedString, container, options = {}) => { finalizeFragments(engines, options), typesetter(engines, options, container), processParagraphs, - splitParagraphs(engines, options), + splitParagraphs(), preprocessRuns(engines, options), - applyDefaultStyles(engines, options), + applyDefaultStyles(), )(attributedString); }; diff --git a/packages/textkit/src/layout/layoutParagraph.js b/packages/textkit/src/layout/layoutParagraph.js index 2c53265c8..c142ba224 100644 --- a/packages/textkit/src/layout/layoutParagraph.js +++ b/packages/textkit/src/layout/layoutParagraph.js @@ -7,15 +7,15 @@ const ATTACHMENT_CODE = '\ufffc'; // 65532 /** * Remove attachment attribute if no char present * - * @param {Object} attributed string - * @return {Object} attributed string + * @param {Object} attributedString attributed string + * @returns {Object} attributed string */ -const purgeAttachments = attributedString => { +const purgeAttachments = (attributedString) => { const shouldPurge = !attributedString.string.includes(ATTACHMENT_CODE); if (!shouldPurge) return attributedString; - const runs = attributedString.runs.map(run => omit('attachment', run)); + const runs = attributedString.runs.map((run) => omit('attachment', run)); return Object.assign({}, attributedString, { runs }); }; @@ -23,9 +23,10 @@ const purgeAttachments = attributedString => { /** * Layout paragraphs inside rectangle * - * @param {Object} rect - * @param {Array} attributed strings - * @return {Object} layout blocks + * @param {Object} rects rect + * @param {Object[]} lines attributed strings + * @param {number} indent + * @returns {Object} layout blocks */ const layoutLines = (rects, lines, indent) => { let rect = rects.shift(); @@ -58,21 +59,26 @@ const layoutLines = (rects, lines, indent) => { }); }; +/** + * @typedef {Function} LayoutParagraph + * @param {Object} container rect + * @param {Object} paragraph attributed string + * @returns {Object} layout block + */ + /** * Performs line breaking and layout * - * @param {Object} engines - * @param {Object} layout options - * @param {Object} rect - * @param {Object} attributed string - * @return {Object} layout block + * @param {Object} engines engines + * @param {Object} options layout options + * @returns {LayoutParagraph} layout paragraph */ const layoutParagraph = (engines, options) => (container, paragraph) => { const height = stringHeight(paragraph); const indent = paragraph.runs?.[0]?.attributes?.indent || 0; const rects = generateLineRects(container, height); - const availableWidths = rects.map(r => r.width); + const availableWidths = rects.map((r) => r.width); availableWidths[0] -= indent; const lines = engines.linebreaker(options)(paragraph, availableWidths); diff --git a/packages/textkit/src/layout/preprocessRuns.js b/packages/textkit/src/layout/preprocessRuns.js index 263e6a135..b2cb26f63 100644 --- a/packages/textkit/src/layout/preprocessRuns.js +++ b/packages/textkit/src/layout/preprocessRuns.js @@ -9,13 +9,18 @@ const omitFont = attributedString => { return Object.assign({}, attributedString, { runs }); }; +/** + * @typedef {Function} PreprocessRuns + * @param {Object} attributedString attributed string + * @returns {Object} processed attributed string + */ + /** * Performs font substitution and script itemization on attributed string * - * @param {Object} engines - * @param {Object} layout options - * @param {Object} attributed string - * @return {Object} processed attributed string + * @param {Object} engines engines + * @param {Object} options layout options + * @returns {PreprocessRuns} preprocess runs */ const preprocessRuns = (engines, options) => attributedString => { if (isNil(attributedString)) return empty(); diff --git a/packages/textkit/src/layout/resolveAttachments.js b/packages/textkit/src/layout/resolveAttachments.js index 823d78033..18e2e9c5d 100644 --- a/packages/textkit/src/layout/resolveAttachments.js +++ b/packages/textkit/src/layout/resolveAttachments.js @@ -5,8 +5,8 @@ const isReplaceGlyph = glyph => glyph.codePoints.includes(ATTACHMENT_CODE); /** * Resolve attachments of run * - * @param {Object} run - * @return {Object} run + * @param {Object} run + * @returns {Object} run */ const resolveRunAttachments = run => { if (!run.positions) return run; @@ -27,13 +27,16 @@ const resolveRunAttachments = run => { return Object.assign({}, run, { positions }); }; +/** + * @typedef {Function} AttachmentResolver + * @param {string} attributedString attributed string + * @returns {string} attributed string + */ + /** * Resolve attachments for multiple paragraphs * - * @param {Object} layout engines - * @param {Object} layout options - * @param {Array} attributed strings (paragraphs) - * @return {Array} attributed strings (paragraphs) + * @returns {AttachmentResolver} attachmentResolver */ const resolveAttachments = () => attributedString => { const runs = attributedString.runs.map(resolveRunAttachments); diff --git a/packages/textkit/src/layout/resolveYOffset.js b/packages/textkit/src/layout/resolveYOffset.js index 068e1d966..c08d28a54 100644 --- a/packages/textkit/src/layout/resolveYOffset.js +++ b/packages/textkit/src/layout/resolveYOffset.js @@ -1,8 +1,8 @@ /** * Resolves yOffset for run * - * @param {Object} run - * @return {Object} run + * @param {Object} run + * @returns {Object} run */ const resolveRunYOffset = run => { if (!run.positions) return run; @@ -14,13 +14,16 @@ const resolveRunYOffset = run => { return Object.assign({}, run, { positions }); }; +/** + * @typedef {Function} YOffsetResolver + * @param {string} attributedString attributed string + * @returns {string} attributed string + */ + /** * Resolves yOffset for multiple paragraphs * - * @param {Object} layout engines - * @param {Object} layout options - * @param {Array} attributed strings (paragraphs) - * @return {Array} attributed strings (paragraphs) + * @returns {YOffsetResolver} yOffsetResolver */ const resolveYOffset = () => attributedString => { const runs = attributedString.runs.map(resolveRunYOffset); diff --git a/packages/textkit/src/layout/splitParagraphs.js b/packages/textkit/src/layout/splitParagraphs.js index 314013e3b..b7d84fe78 100644 --- a/packages/textkit/src/layout/splitParagraphs.js +++ b/packages/textkit/src/layout/splitParagraphs.js @@ -1,15 +1,18 @@ import length from '../attributedString/length'; import slice from '../attributedString/slice'; +/** + * @typedef {Function} SplitParagraphs + * @param {Object} attributedString attributed string + * @returns {Object[]} attributed string array + */ + /** * Breaks attributed string into paragraphs * - * @param {Object} engines - * @param {Object} layout options - * @param {Object} attributed string - * @return {Array} attributed string array + * @returns {SplitParagraphs} split paragraphs */ -const splitParagraphs = () => attributedString => { +const splitParagraphs = () => (attributedString) => { const res = []; let start = 0; diff --git a/packages/textkit/src/layout/typesetter.js b/packages/textkit/src/layout/typesetter.js index 0a6069e0f..3e6e88c91 100644 --- a/packages/textkit/src/layout/typesetter.js +++ b/packages/textkit/src/layout/typesetter.js @@ -7,17 +7,22 @@ import truncateBlock from '../block/truncate'; import layoutParagraph from './layoutParagraph'; import sliceBlockAtHeight from '../block/sliceAtHeight'; +/** + * @typedef {Function} TypeSetter + * @param {Object} attributedStrings attributed strings (paragraphs) + * @returns {Object[]} paragraph blocks + */ + /** * Layout paragraphs inside container until it does not * fit anymore, performing line wrapping in the process. * - * @param {Object} engines - * @param {Object} layout options - * @param {Object} container rect - * @param {Object} attributed strings (paragraphs) - * @return {Array} paragraph blocks + * @param {Object} engines engines + * @param {Object} options layout options + * @param {Object} container container rect + * @returns {TypeSetter} type setter */ -const typesetter = (engines, options, container) => attributedStrings => { +const typesetter = (engines, options, container) => (attributedStrings) => { const blocks = []; const paragraphs = [...attributedStrings]; const layoutBlock = layoutParagraph(engines, options); diff --git a/packages/textkit/src/layout/verticalAlign.js b/packages/textkit/src/layout/verticalAlign.js index dc0c2dc3e..e966d6e23 100644 --- a/packages/textkit/src/layout/verticalAlign.js +++ b/packages/textkit/src/layout/verticalAlign.js @@ -1,11 +1,15 @@ /* eslint-disable no-restricted-syntax */ +/** + * @typedef {Function} VerticalAlignment + * @param {Object} attributedString attributed string + * @returns {Object} attributed string + */ + /** * Apply scaling and yOffset for verticalAlign 'sub' and 'super'. * - * @param {Object} layout options - * @param {Object} attributed string - * @return {Object} attributed string + * @returns {VerticalAlignment} verticalAlignment */ const verticalAlignment = () => attributedString => { attributedString.runs.forEach(run => { diff --git a/packages/textkit/src/layout/wrapWords.js b/packages/textkit/src/layout/wrapWords.js index 12b8a4c43..7725f7eee 100644 --- a/packages/textkit/src/layout/wrapWords.js +++ b/packages/textkit/src/layout/wrapWords.js @@ -4,48 +4,55 @@ import fromFragments from '../attributedString/fromFragments'; * Default word hyphenation engine used when no one provided. * Does not perform word hyphenation at all * - * @param {String} word - * @return {Array} same word + * @param {string} word + * @returns {[string]} same word + */ +const defaultHyphenationEngine = (word) => [word]; + +/** + * @typedef {Function} HyphenationCallback + * @param {Object} attributedString attributed string + * @returns {Object} attributed string including syllables */ -const defaultHyphenationEngine = word => [word]; /** * Wrap words of attribute string * - * @param {Object} layout engines - * @param {Object} layout options - * @param {Object} attributed string - * @return {Object} attributed string including syllables + * @param {Object} engines layout engines + * @param {Object} options layout options + * @returns {HyphenationCallback} hyphenation callback */ -const wrapWords = (engines = {}, options = {}) => attributedString => { - const syllables = []; - const fragments = []; - - const hyphenateWord = - options.hyphenationCallback || - engines.wordHyphenation?.(options) || - defaultHyphenationEngine; - - for (let i = 0; i < attributedString.runs.length; i += 1) { - let string = ''; - const run = attributedString.runs[i]; - const words = attributedString.string - .slice(run.start, run.end) - .split(/([ ]+)/g) - .filter(Boolean); - - for (let j = 0; j < words.length; j += 1) { - const word = words[j]; - const parts = hyphenateWord(word); - - syllables.push(...parts); - string += parts.join(''); +const wrapWords = + (engines = {}, options = {}) => + (attributedString) => { + const syllables = []; + const fragments = []; + + const hyphenateWord = + options.hyphenationCallback || + engines.wordHyphenation?.(options) || + defaultHyphenationEngine; + + for (let i = 0; i < attributedString.runs.length; i += 1) { + let string = ''; + const run = attributedString.runs[i]; + const words = attributedString.string + .slice(run.start, run.end) + .split(/([ ]+)/g) + .filter(Boolean); + + for (let j = 0; j < words.length; j += 1) { + const word = words[j]; + const parts = hyphenateWord(word); + + syllables.push(...parts); + string += parts.join(''); + } + + fragments.push({ string, attributes: run.attributes }); } - fragments.push({ string, attributes: run.attributes }); - } - - return { ...fromFragments(fragments), syllables }; -}; + return { ...fromFragments(fragments), syllables }; + }; export default wrapWords; diff --git a/packages/textkit/src/positions/advanceWidth.js b/packages/textkit/src/positions/advanceWidth.js index 94721b98c..140384976 100644 --- a/packages/textkit/src/positions/advanceWidth.js +++ b/packages/textkit/src/positions/advanceWidth.js @@ -1,8 +1,8 @@ /** * Return positions advance width * - * @param {Object} positions - * @return {number} advance width + * @param {Object} positions + * @returns {number} advance width */ const advanceWidth = positions => { return positions.reduce((acc, pos) => acc + (pos.xAdvance || 0), 0); diff --git a/packages/textkit/src/rect/area.js b/packages/textkit/src/rect/area.js index 517e3edc3..c3bc48ee9 100644 --- a/packages/textkit/src/rect/area.js +++ b/packages/textkit/src/rect/area.js @@ -1,8 +1,8 @@ /** * Returns rect area * - * @param {Object} rect - * @return {number} rect area + * @param {Object} rect + * @returns {number} rect area */ const area = rect => { return rect ? rect.height * rect.width : 0; diff --git a/packages/textkit/src/rect/bottomLeft.js b/packages/textkit/src/rect/bottomLeft.js index 2f9a1ec31..a25bc5b70 100644 --- a/packages/textkit/src/rect/bottomLeft.js +++ b/packages/textkit/src/rect/bottomLeft.js @@ -5,8 +5,8 @@ const ZERO = { x: 0, y: 0 }; /** * Returns rect bottom left point * - * @param {Object} rect - * @return {number} bottom left point + * @param {Object} rect rect + * @returns {{ x: number, y: number }} bottom left point */ const bottomLeft = rect => { return rect ? { x: rect.x || 0, y: maxY(rect) } : ZERO; diff --git a/packages/textkit/src/rect/bottomRight.js b/packages/textkit/src/rect/bottomRight.js index b86761f7e..bfd9164e5 100644 --- a/packages/textkit/src/rect/bottomRight.js +++ b/packages/textkit/src/rect/bottomRight.js @@ -4,8 +4,8 @@ import maxY from './maxY'; /** * Returns rect bottom right point * - * @param {Object} rect - * @return {number} bottom right point + * @param {Object} rect rect + * @returns {{ x:number, y:number }} bottom right point */ const bottomRight = rect => ({ x: maxX(rect), y: maxY(rect) }); diff --git a/packages/textkit/src/rect/copy.js b/packages/textkit/src/rect/copy.js index 4dc7d3998..48f805661 100644 --- a/packages/textkit/src/rect/copy.js +++ b/packages/textkit/src/rect/copy.js @@ -1,8 +1,8 @@ /** * Clone rect * - * @param {Object} rect - * @return {Object} cloned rect + * @param {Object} rect + * @returns {Object} cloned rect */ const copy = rect => Object.assign({}, rect); diff --git a/packages/textkit/src/rect/crop.js b/packages/textkit/src/rect/crop.js index 9e37f8743..c8123bfa1 100644 --- a/packages/textkit/src/rect/crop.js +++ b/packages/textkit/src/rect/crop.js @@ -3,8 +3,8 @@ import partition from './partition'; /** * Crop upper section of rect * - * @param {Object} rect - * @return {Object} cropped rect + * @param {Object} rect + * @returns {Object} cropped rect */ const crop = (height, rect) => { const [, result] = partition(rect, height); diff --git a/packages/textkit/src/rect/empty.js b/packages/textkit/src/rect/empty.js index b859073c8..bf6ddb82e 100644 --- a/packages/textkit/src/rect/empty.js +++ b/packages/textkit/src/rect/empty.js @@ -1,7 +1,7 @@ /** * Returns empty rect * - * @return {Object} empty rect + * @returns {Object} empty rect */ const empty = () => ({ x: 0, diff --git a/packages/textkit/src/rect/equals.js b/packages/textkit/src/rect/equals.js index 4ababb684..d37a05fc9 100644 --- a/packages/textkit/src/rect/equals.js +++ b/packages/textkit/src/rect/equals.js @@ -1,9 +1,9 @@ /** * Check if two rect are equal * - * @param {Object} rect A - * @param {Object} rect B - * @return {Boolean} rects are equal + * @param {Object} a rect A + * @param {Object} b rect B + * @returns {boolean} rects are equal * */ const equals = (a, b) => { diff --git a/packages/textkit/src/rect/intersects.js b/packages/textkit/src/rect/intersects.js index a796ce51c..4cfa7f2d4 100644 --- a/packages/textkit/src/rect/intersects.js +++ b/packages/textkit/src/rect/intersects.js @@ -1,9 +1,17 @@ +/** + * @typedef {Object} Rect + * @property {number} x + * @property {number} y + * @property {number} width + * @property {number} height + */ + /** * Checks if two rects intersect each other * * @param {Rect} a * @param {Rect} b - * @returns {Boolean} rects intersects + * @returns {boolean} rects intersects */ const intersects = (a, b) => { const x = Math.max(a.x, b.x); diff --git a/packages/textkit/src/rect/maxX.js b/packages/textkit/src/rect/maxX.js index 473b26507..423a52e06 100644 --- a/packages/textkit/src/rect/maxX.js +++ b/packages/textkit/src/rect/maxX.js @@ -1,8 +1,8 @@ /** * Returns max rect X coordinate * - * @param {Object} rect - * @return {number} x coordinate + * @param {Object} rect + * @returns {number} x coordinate */ const maxX = rect => { return rect ? rect.x + rect.width : 0; diff --git a/packages/textkit/src/rect/maxY.js b/packages/textkit/src/rect/maxY.js index 5c6952717..01380a339 100644 --- a/packages/textkit/src/rect/maxY.js +++ b/packages/textkit/src/rect/maxY.js @@ -1,8 +1,8 @@ /** * Returns max rect Y coordinate * - * @param {Object} rect - * @return {number} y coordinate + * @param {Object} rect + * @returns {number} y coordinate */ const maxY = rect => { return rect ? rect.y + rect.height : 0; diff --git a/packages/textkit/src/run/add.js b/packages/textkit/src/run/add.js index cd1885497..34ab601ef 100644 --- a/packages/textkit/src/run/add.js +++ b/packages/textkit/src/run/add.js @@ -1,9 +1,9 @@ /** * Add scalar to run * - * @param {number} scalar - * @param {Object} run - * @return {Object} added run + * @param {number} n scalar + * @param {Object} run run + * @returns {Object} added run */ const add = (n, run) => { const start = run.start + n; diff --git a/packages/textkit/src/run/advanceWidth.js b/packages/textkit/src/run/advanceWidth.js index 24d9deddf..6fe722f7c 100644 --- a/packages/textkit/src/run/advanceWidth.js +++ b/packages/textkit/src/run/advanceWidth.js @@ -3,8 +3,8 @@ import positionsAdvanceWidth from '../positions/advanceWidth'; /** * Return run advance width * - * @param {Object} run - * @return {number} advance width + * @param {Object} run + * @returns {number} advance width */ const advanceWidth = run => { return positionsAdvanceWidth(run.positions || []); diff --git a/packages/textkit/src/run/advanceWidthBetween.js b/packages/textkit/src/run/advanceWidthBetween.js index db380b999..06c131b48 100644 --- a/packages/textkit/src/run/advanceWidthBetween.js +++ b/packages/textkit/src/run/advanceWidthBetween.js @@ -4,10 +4,10 @@ import positionsAdvanceWidth from '../positions/advanceWidth'; /** * Advance width between two string indices * - * @param {number} start glyph index - * @param {number} end glyph index - * @param {Object} run - * @return {Object} advanced width run + * @param {number} start glyph index + * @param {number} end glyph index + * @param {Object} run + * @returns {Object} advanced width run */ const advanceWidthBetween = (start, end, run) => { const runStart = run.start || 0; diff --git a/packages/textkit/src/run/append.js b/packages/textkit/src/run/append.js index 4e013284d..e6c1c1014 100644 --- a/packages/textkit/src/run/append.js +++ b/packages/textkit/src/run/append.js @@ -7,9 +7,9 @@ import glyphFromCodePoint from '../glyph/fromCodePoint'; /** * Append glyph to run * - * @param {Object} glyph - * @param {Object} run - * @return {Object} run with glyph + * @param {Object} glyph + * @param {Object} run + * @returns {Object} run with glyph */ const appendGlyph = (glyph, run) => { const glyphLength = glyph.codePoints?.length || 0; @@ -30,9 +30,9 @@ const appendGlyph = (glyph, run) => { /** * Append glyph or code point to run * - * @param {Object | number} glyph | codePoint - * @param {Object} run - * @return {Object} run with glyph + * @param {Object | number} value glyph | codePoint + * @param {Object} run + * @returns {Object} run with glyph */ const append = (value, run) => { if (!value) return run; diff --git a/packages/textkit/src/run/ascent.js b/packages/textkit/src/run/ascent.js index 9c929cc0e..cf89184e0 100644 --- a/packages/textkit/src/run/ascent.js +++ b/packages/textkit/src/run/ascent.js @@ -3,8 +3,8 @@ import scale from './scale'; /** * Get run ascent * - * @param {Object} run - * @return {boolean} ascent + * @param {Object} run + * @returns {number} ascent */ const ascent = run => { const attachmentHeight = run.attributes?.attachment?.height || 0; diff --git a/packages/textkit/src/run/concat.js b/packages/textkit/src/run/concat.js index 4595f1ea2..eb1329fda 100644 --- a/packages/textkit/src/run/concat.js +++ b/packages/textkit/src/run/concat.js @@ -6,9 +6,9 @@ import normalizeIndices from '../indices/normalize'; /** * Concats two runs into one * - * @param {Object} first run - * @param {Object} second run - * @return {Object} concatenated run + * @param {Object} runA first run + * @param {Object} runB second run + * @returns {Object} concatenated run */ const concat = (runA, runB) => { const end = runA.end + length(runB); diff --git a/packages/textkit/src/run/descent.js b/packages/textkit/src/run/descent.js index 3b1709d50..db3561b5b 100644 --- a/packages/textkit/src/run/descent.js +++ b/packages/textkit/src/run/descent.js @@ -3,8 +3,8 @@ import scale from './scale'; /** * Get run descent * - * @param {Object} run - * @return {number} descent + * @param {Object} run + * @returns {number} descent */ const descent = run => { const fontDescent = run.attributes?.font?.descent || 0; diff --git a/packages/textkit/src/run/dropLast.js b/packages/textkit/src/run/dropLast.js index 6821c9847..3dd94a7ad 100644 --- a/packages/textkit/src/run/dropLast.js +++ b/packages/textkit/src/run/dropLast.js @@ -3,8 +3,8 @@ import slice from './slice'; /** * Drop last char of run * - * @param {Object} run - * @return {boolean} run without last char + * @param {Object} run + * @returns {Object} run without last char */ const dropLast = run => slice(0, run.end - run.start - 1, run); diff --git a/packages/textkit/src/run/empty.js b/packages/textkit/src/run/empty.js index d2c74b8c5..95d3e37f4 100644 --- a/packages/textkit/src/run/empty.js +++ b/packages/textkit/src/run/empty.js @@ -1,7 +1,7 @@ /** * Returns empty run * - * @return {Object} empty run + * @returns {Object} empty run */ const empty = () => ({ start: 0, diff --git a/packages/textkit/src/run/filter.js b/packages/textkit/src/run/filter.js index 68b71e134..698895e89 100644 --- a/packages/textkit/src/run/filter.js +++ b/packages/textkit/src/run/filter.js @@ -3,10 +3,10 @@ import runIndexAt from './runIndexAt'; /** * Filter runs contained between start and end * - * @param {number} start - * @param {number} end - * @param {Array} runs - * @return {boolean} filtered runs + * @param {number} start + * @param {number} end + * @param {Object[]} runs + * @returns {Object} filtered runs */ const filter = (start, end, runs) => { const startIndex = runIndexAt(start, runs); diff --git a/packages/textkit/src/run/flatten.js b/packages/textkit/src/run/flatten.js index c34f874e3..5eaf21718 100644 --- a/packages/textkit/src/run/flatten.js +++ b/packages/textkit/src/run/flatten.js @@ -3,7 +3,7 @@ import isEmpty from './isEmpty'; const sortPoints = (a, b) => a[1] - b[1] || a[3] - b[3]; -const generatePoints = runs => { +const generatePoints = (runs) => { const result = runs.reduce((acc, run, i) => { return acc.concat([ ['start', run.start, run.attributes, i], @@ -14,13 +14,13 @@ const generatePoints = runs => { return result.sort(sortPoints); }; -const mergeRuns = runs => +const mergeRuns = (runs) => runs.reduce((acc, run) => { const attributes = Object.assign({}, acc.attributes, run.attributes); return Object.assign({}, run, { attributes }); }, {}); -const groupEmptyRuns = runs => { +const groupEmptyRuns = (runs) => { const groups = runs.reduce((acc, run) => { if (!acc[run.start]) acc[run.start] = []; acc[run.start].push(run); @@ -30,11 +30,11 @@ const groupEmptyRuns = runs => { return Object.values(groups); }; -const flattenEmptyRuns = runs => { +const flattenEmptyRuns = (runs) => { return groupEmptyRuns(runs).map(mergeRuns); }; -const flattenRegularRuns = runs => { +const flattenRegularRuns = (runs) => { const res = []; const points = generatePoints(runs); @@ -74,12 +74,12 @@ const flattenRegularRuns = runs => { /** * Flatten many runs * - * @param {Array} runs - * @return {Array} flatten runs + * @param {Object[]} runs + * @returns {Object[]} flatten runs */ const flatten = (runs = []) => { - const emptyRuns = flattenEmptyRuns(runs.filter(run => isEmpty(run))); - const regularRuns = flattenRegularRuns(runs.filter(run => !isEmpty(run))); + const emptyRuns = flattenEmptyRuns(runs.filter((run) => isEmpty(run))); + const regularRuns = flattenRegularRuns(runs.filter((run) => !isEmpty(run))); return sort(emptyRuns.concat(regularRuns)); }; diff --git a/packages/textkit/src/run/getFont.js b/packages/textkit/src/run/getFont.js index 182043e76..295f842f1 100644 --- a/packages/textkit/src/run/getFont.js +++ b/packages/textkit/src/run/getFont.js @@ -1,8 +1,8 @@ /** * Get run font * - * @param {Object} run - * @return {Object} font + * @param {Object} run + * @returns {Object} font */ const getFont = run => run.attributes?.font || null; diff --git a/packages/textkit/src/run/glyphIndexAt.js b/packages/textkit/src/run/glyphIndexAt.js index ca7367d61..915b2ff5b 100644 --- a/packages/textkit/src/run/glyphIndexAt.js +++ b/packages/textkit/src/run/glyphIndexAt.js @@ -4,9 +4,9 @@ import { isNil } from '@react-pdf/fns'; * Return glyph index at string index, if glyph indices present. * Otherwise return string index * - * @param {number} string index - * @param {Object} run - * @return {number} glyph index + * @param {number} index index + * @param {Object} run + * @returns {number} glyph index */ const glyphIndexAt = (index, run) => { const result = run?.glyphIndices?.[index]; diff --git a/packages/textkit/src/run/height.js b/packages/textkit/src/run/height.js index ec8e44705..eea5297ef 100644 --- a/packages/textkit/src/run/height.js +++ b/packages/textkit/src/run/height.js @@ -5,8 +5,8 @@ import lineGap from './lineGap'; /** * Get run height * - * @param {Object} run - * @return {number} height + * @param {Object} run + * @returns {number} height */ const height = run => { const lineHeight = run.attributes?.lineHeight; diff --git a/packages/textkit/src/run/indexAtOffset.js b/packages/textkit/src/run/indexAtOffset.js index 75aaf137e..9b8bd1e44 100644 --- a/packages/textkit/src/run/indexAtOffset.js +++ b/packages/textkit/src/run/indexAtOffset.js @@ -1,9 +1,9 @@ /** * Get string index at offset * - * @param {Object} run - * @param {number} offset - * @return {number} string index at offset N + * @param {number} offset + * @param {Object} run + * @returns {number} string index at offset N */ const indexAtOffset = (offset, run) => { let counter = 0; diff --git a/packages/textkit/src/run/insert.js b/packages/textkit/src/run/insert.js index 99ab98038..8b9ad8343 100644 --- a/packages/textkit/src/run/insert.js +++ b/packages/textkit/src/run/insert.js @@ -8,10 +8,10 @@ import glyphFromCodePoint from '../glyph/fromCodePoint'; /** * Insert glyph to run in the given index * - * @param {number} string index - * @param {Object} glyph - * @param {Object} run - * @return {Object} run with glyph + * @param {number} index index + * @param {Object} glyph + * @param {Object} run + * @returns {Object} run with glyph */ const insertGlyph = (index, glyph, run) => { if (!glyph) return run; @@ -26,10 +26,10 @@ const insertGlyph = (index, glyph, run) => { /** * Insert either glyph or code point to run in the given index * - * @param {number} string index - * @param {Object | number} glyph | codePoint - * @param {Object} run - * @return {Object} run with glyph + * @param {number} index index + * @param {Object | number} value glyph | codePoint + * @param {Object} run + * @returns {Object} run with glyph */ const insert = (index, value, run) => { const font = getFont(run); diff --git a/packages/textkit/src/run/isEmpty.js b/packages/textkit/src/run/isEmpty.js index d0e248176..4485334ea 100644 --- a/packages/textkit/src/run/isEmpty.js +++ b/packages/textkit/src/run/isEmpty.js @@ -1,8 +1,8 @@ /** * Is run empty (start === end) * - * @param {Object} run - * @return {Object} is run empty + * @param {Object} run + * @returns {Object} is run empty */ const isEmpty = run => { return run.start === run.end; diff --git a/packages/textkit/src/run/leadingOffset.js b/packages/textkit/src/run/leadingOffset.js index 0ba78c13a..6bd9e5e10 100644 --- a/packages/textkit/src/run/leadingOffset.js +++ b/packages/textkit/src/run/leadingOffset.js @@ -3,13 +3,13 @@ import isWhiteSpace from '../glyph/isWhiteSpace'; /** * Get white space leading positions * - * @param {Object} run - * @return {Array} white space leading positions + * @param {Object} run + * @returns {Object[]} white space leading positions */ -const leadingPositions = run => { +const leadingPositions = (run) => { const glyphs = run.glyphs || []; const positions = run.positions || []; - const leadingWhitespaces = glyphs.findIndex(g => !isWhiteSpace(g)); + const leadingWhitespaces = glyphs.findIndex((g) => !isWhiteSpace(g)); return positions.slice(0, leadingWhitespaces); }; @@ -17,10 +17,10 @@ const leadingPositions = run => { /** * Get run leading white space offset * - * @param {Object} run - * @return {number} leading white space offset + * @param {Object} run + * @returns {number} leading white space offset */ -const leadingOffset = run => { +const leadingOffset = (run) => { const positions = leadingPositions(run); return positions.reduce((acc, pos) => acc + (pos.xAdvance || 0), 0); diff --git a/packages/textkit/src/run/length.js b/packages/textkit/src/run/length.js index e5efc0e68..81ae4e2e7 100644 --- a/packages/textkit/src/run/length.js +++ b/packages/textkit/src/run/length.js @@ -1,8 +1,8 @@ /** * Get run length * - * @param {Object} run - * @return {number} length + * @param {Object} run + * @returns {number} length */ const length = run => { return run.end - run.start; diff --git a/packages/textkit/src/run/lineGap.js b/packages/textkit/src/run/lineGap.js index 96a51d604..a19331059 100644 --- a/packages/textkit/src/run/lineGap.js +++ b/packages/textkit/src/run/lineGap.js @@ -3,8 +3,8 @@ import scale from './scale'; /** * Get run lineGap * - * @param {Object} run - * @return {number} lineGap + * @param {Object} run + * @returns {number} lineGap */ const lineGap = run => { return (run.attributes?.font?.lineGap || 0) * scale(run); diff --git a/packages/textkit/src/run/offset.js b/packages/textkit/src/run/offset.js index 2e18773f4..631dde0d1 100644 --- a/packages/textkit/src/run/offset.js +++ b/packages/textkit/src/run/offset.js @@ -7,9 +7,9 @@ * glyphIndices: 0 1 2 2 2 3 * offset: 0 0 0 1 2 0 * - * @param {number} index - * @param {Object} run - * @return {number} ligature offset + * @param {number} index + * @param {Object} run + * @returns {number} ligature offset */ const offset = (index, run) => { if (!run) return 0; diff --git a/packages/textkit/src/run/omit.js b/packages/textkit/src/run/omit.js index 3e00371e5..5cd53c6be 100644 --- a/packages/textkit/src/run/omit.js +++ b/packages/textkit/src/run/omit.js @@ -1,8 +1,8 @@ /** * Omit attribute from run * - * @param {Object} run - * @return {Object} run without ommited attribute + * @param {Object} run + * @returns {Object} run without ommited attribute */ const omit = (value, run) => { const attributes = Object.assign({}, run.attributes); diff --git a/packages/textkit/src/run/prepend.js b/packages/textkit/src/run/prepend.js index 9ed4cb825..d77871327 100644 --- a/packages/textkit/src/run/prepend.js +++ b/packages/textkit/src/run/prepend.js @@ -7,9 +7,9 @@ import glyphFromCodePoint from '../glyph/fromCodePoint'; /** * Prepend glyph to run * - * @param {Object} glyph - * @param {Object} run - * @return {Object} run with glyph + * @param {Object} glyph + * @param {Object} run + * @returns {Object} run with glyph */ const prependGlyph = (glyph, run) => { const runScale = scale(run); @@ -28,9 +28,9 @@ const prependGlyph = (glyph, run) => { /** * Prepend glyph or code point on run * - * @param {Object | number} glyph | codePoint - * @param {Object} run - * @return {Object} run with glyph + * @param {Object | number} value glyph or codePoint + * @param {Object} run + * @returns {Object} run with glyph */ const prepend = (value, run) => { if (!value) return run; diff --git a/packages/textkit/src/run/runIndexAt.js b/packages/textkit/src/run/runIndexAt.js index 852581e24..16aea1852 100644 --- a/packages/textkit/src/run/runIndexAt.js +++ b/packages/textkit/src/run/runIndexAt.js @@ -1,14 +1,14 @@ /** * Get run index that contains passed index * - * @param {number} char index - * @param {Array} runs array - * @return {Array} run index + * @param {number} n index + * @param {{ start: number, end: number }[]} runs array + * @returns {number} run index */ const runIndexAt = (n, runs) => { if (!runs) return -1; - return runs.findIndex(run => run.start <= n && n < run.end); + return runs.findIndex((run) => run.start <= n && n < run.end); }; export default runIndexAt; diff --git a/packages/textkit/src/run/scale.js b/packages/textkit/src/run/scale.js index 172907722..57484ec2c 100644 --- a/packages/textkit/src/run/scale.js +++ b/packages/textkit/src/run/scale.js @@ -1,8 +1,8 @@ /** * Calculate run scale * - * @param {Object} run - * @return {number} scale + * @param {Object} run + * @returns {number} scale */ const calculateScale = run => { const attributes = run.attributes || {}; @@ -15,8 +15,8 @@ const calculateScale = run => { /** * Get run scale * - * @param {Object} run - * @return {number} scale + * @param {Object} run + * @returns {number} scale */ const scale = run => { return run.attributes?.scale || calculateScale(run); diff --git a/packages/textkit/src/run/slice.js b/packages/textkit/src/run/slice.js index ee79063b0..0935b08ec 100644 --- a/packages/textkit/src/run/slice.js +++ b/packages/textkit/src/run/slice.js @@ -8,10 +8,10 @@ import normalizeIndices from '../indices/normalize'; /** * Slice run between glyph indices range * - * @param {number} start glyph index - * @param {number} end glyph index - * @param {Object} run - * @return {Object} sliced run + * @param {number} start glyph index + * @param {number} end glyph index + * @param {Object} run + * @returns {Object} sliced run */ const slice = (start, end, run) => { const runScale = scale(run); diff --git a/packages/textkit/src/run/sort.js b/packages/textkit/src/run/sort.js index 6acbe8392..f4c1a512f 100644 --- a/packages/textkit/src/run/sort.js +++ b/packages/textkit/src/run/sort.js @@ -1,9 +1,10 @@ /** * Sort runs in ascending order * - * @param {Array} runs - * @return {Array} sorted runs + * @template {{ start: number, end: number }} T + * @param {T[]} runs + * @returns {T[]} sorted runs */ -const sort = runs => runs.sort((a, b) => a.start - b.start || a.end - b.end); +const sort = (runs) => runs.sort((a, b) => a.start - b.start || a.end - b.end); export default sort; diff --git a/packages/textkit/src/run/subtract.js b/packages/textkit/src/run/subtract.js index e7dad0f57..ba34b3e27 100644 --- a/packages/textkit/src/run/subtract.js +++ b/packages/textkit/src/run/subtract.js @@ -1,9 +1,9 @@ /** * Subtract scalar to run * - * @param {number} scalar - * @param {Object} run - * @return {Object} subtracted run + * @param {number} n scalar + * @param {Object} run + * @returns {Object} subtracted run */ const subtract = (n, run) => { const start = run.start - n; diff --git a/packages/textkit/src/run/trailingOffset.js b/packages/textkit/src/run/trailingOffset.js index 7dc45e0b8..fcdcdc9b1 100644 --- a/packages/textkit/src/run/trailingOffset.js +++ b/packages/textkit/src/run/trailingOffset.js @@ -1,17 +1,22 @@ import isWhiteSpace from '../glyph/isWhiteSpace'; -const reverse = array => [...array].reverse(); +/** + * @template T + * @param {T[]} array + * @returns {T[]} reversed array + */ +const reverse = (array) => [...array].reverse(); /** * Get white space trailing positions * - * @param {Object} run - * @return {Array} white space trailing positions + * @param {Object} run + * @returns {Object[]} white space trailing positions */ -const trailingPositions = run => { +const trailingPositions = (run) => { const glyphs = reverse(run.glyphs || []); const positions = reverse(run.positions || []); - const leadingWhitespaces = glyphs.findIndex(g => !isWhiteSpace(g)); + const leadingWhitespaces = glyphs.findIndex((g) => !isWhiteSpace(g)); return positions.slice(0, leadingWhitespaces); }; @@ -19,10 +24,10 @@ const trailingPositions = run => { /** * Get run trailing white space offset * - * @param {Object} run - * @return {number} trailing white space offset + * @param {Object} run + * @returns {number} trailing white space offset */ -const trailingOffset = run => { +const trailingOffset = (run) => { const positions = trailingPositions(run); return positions.reduce((acc, pos) => acc + (pos.xAdvance || 0), 0); diff --git a/packages/textkit/src/utils/stringFromCodePoints.js b/packages/textkit/src/utils/stringFromCodePoints.js index 577db7182..2ddace913 100644 --- a/packages/textkit/src/utils/stringFromCodePoints.js +++ b/packages/textkit/src/utils/stringFromCodePoints.js @@ -1,8 +1,8 @@ /** * Get string from array of code points * - * @param {Array} code points - * @return {String} string + * @param {number[]} codePoints points + * @returns {string} string */ const stringFromCodePoints = codePoints => String.fromCodePoint(...codePoints); diff --git a/packages/textkit/tests/engines/fontSubstitution.test.js b/packages/textkit/tests/engines/fontSubstitution.test.js index 3bc6507a7..bc3097f62 100644 --- a/packages/textkit/tests/engines/fontSubstitution.test.js +++ b/packages/textkit/tests/engines/fontSubstitution.test.js @@ -1,7 +1,7 @@ import empty from '../../src/attributedString/empty'; import fontSubstitution from '../../src/engines/fontSubstitution'; -const instance = fontSubstitution({}); +const instance = fontSubstitution(); describe('FontSubstitution', () => { test('should return empty array if no runs passed', () => { diff --git a/packages/textkit/tests/engines/scriptItemizer.test.js b/packages/textkit/tests/engines/scriptItemizer.test.js index 8d058b522..65b00d012 100644 --- a/packages/textkit/tests/engines/scriptItemizer.test.js +++ b/packages/textkit/tests/engines/scriptItemizer.test.js @@ -1,6 +1,6 @@ import scriptItemizer from '../../src/engines/scriptItemizer'; -const instance = scriptItemizer({}); +const instance = scriptItemizer(); describe('scriptItemizer', () => { test('should return empty array for empty string', () => { diff --git a/packages/textkit/tests/engines/wordHyphenation.test.js b/packages/textkit/tests/engines/wordHyphenation.test.js index 701ca97c0..9366a8de3 100644 --- a/packages/textkit/tests/engines/wordHyphenation.test.js +++ b/packages/textkit/tests/engines/wordHyphenation.test.js @@ -14,7 +14,7 @@ jest.unstable_mockModule('hyphen', () => ({ default: () => hyphenator })); const wordHyphenation = (await import('../../src/engines/wordHyphenation')) .default; -const instance = wordHyphenation({}); +const instance = wordHyphenation(); describe('wordHyphenation', () => { beforeEach(() => { diff --git a/packages/textkit/tests/internal/fontSubstitutionEngine.js b/packages/textkit/tests/internal/fontSubstitutionEngine.js index c93529c2a..9e44bbc11 100644 --- a/packages/textkit/tests/internal/fontSubstitutionEngine.js +++ b/packages/textkit/tests/internal/fontSubstitutionEngine.js @@ -7,8 +7,8 @@ import { jest } from '@jest/globals'; * L o r e m * |- Courier -|-- Helvetica --| * - * @param {Object} attributed string - * @return {Object} attributed string + * @param {Object} attributed string + * @returns {Object} attributed string */ export const fontSubstitutionImpl = jest.fn(string => { const runs = diff --git a/packages/textkit/tests/internal/scriptItemizer.js b/packages/textkit/tests/internal/scriptItemizer.js index e4cbbb1aa..e8b9f664b 100644 --- a/packages/textkit/tests/internal/scriptItemizer.js +++ b/packages/textkit/tests/internal/scriptItemizer.js @@ -7,8 +7,8 @@ import { jest } from '@jest/globals'; * L o r e m * |---- Latin ----|- Non-latin-| * - * @param {Object} attributed string - * @return {Object} attributed string + * @param {Object} attributed string + * @returns {Object} attributed string */ export const scriptItemizerImpl = jest.fn(string => { const runs = diff --git a/packages/textkit/tests/run/indexAtOffset.test.js b/packages/textkit/tests/run/indexAtOffset.test.js index dd6edb07b..623b89f9d 100644 --- a/packages/textkit/tests/run/indexAtOffset.test.js +++ b/packages/textkit/tests/run/indexAtOffset.test.js @@ -26,7 +26,7 @@ describe('run indexAtOffset operator', () => { ], }; - expect(indexAtOffset(run, 5)).toBe(0); + expect(indexAtOffset(5, run)).toBe(0); }); test('should return 0 if glyphs empty', () => { @@ -43,7 +43,7 @@ describe('run indexAtOffset operator', () => { ], }; - expect(indexAtOffset(run, 5)).toBe(0); + expect(indexAtOffset(5, run)).toBe(0); }); test('should return correct index', () => {