react-json-tree
Version: 
React JSON Viewer Component, Extracted from redux-devtools
46 lines (45 loc) • 3.14 kB
JavaScript
import React, { useCallback, useState } from 'react';
import JSONArrow from './JSONArrow.js';
import getCollectionEntries from './getCollectionEntries.js';
import JSONNode from './JSONNode.js';
import ItemRange from './ItemRange.js';
function isRange(rangeOrEntry) {
    return rangeOrEntry.to !== undefined;
}
function renderChildNodes(props, from, to) {
    const { nodeType, data, collectionLimit, circularCache, keyPath, postprocessValue, sortObjectKeys, } = props;
    const childNodes = [];
    getCollectionEntries(nodeType, data, sortObjectKeys, collectionLimit, from, to).forEach((entry) => {
        if (isRange(entry)) {
            childNodes.push(React.createElement(ItemRange, { ...props, key: `ItemRange--${entry.from}-${entry.to}`, from: entry.from, to: entry.to, renderChildNodes: renderChildNodes }));
        }
        else {
            const { key, value } = entry;
            const isCircular = circularCache.includes(value);
            childNodes.push(React.createElement(JSONNode, { ...props, postprocessValue, collectionLimit, key: `Node--${key}`, keyPath: [key, ...keyPath], value: postprocessValue(value), circularCache: [...circularCache, value], isCircular: isCircular, hideRoot: false }));
        }
    });
    return childNodes;
}
export default function JSONNestedNode(props) {
    const { circularCache = [], collectionLimit, createItemString, data, expandable, getItemString, hideRoot, isCircular, keyPath, labelRenderer, level = 0, nodeType, nodeTypeIndicator, shouldExpandNodeInitially, styling, } = props;
    const [expanded, setExpanded] = useState(
    // calculate individual node expansion if necessary
    isCircular ? false : shouldExpandNodeInitially(keyPath, data, level));
    const handleClick = useCallback(() => {
        if (expandable)
            setExpanded(!expanded);
    }, [expandable, expanded]);
    const renderedChildren = expanded || (hideRoot && level === 0)
        ? renderChildNodes({ ...props, circularCache, level: level + 1 })
        : null;
    const itemType = (React.createElement("span", { ...styling('nestedNodeItemType', expanded) }, nodeTypeIndicator));
    const renderedItemString = getItemString(nodeType, data, itemType, createItemString(data, collectionLimit), keyPath);
    const stylingArgs = [keyPath, nodeType, expanded, expandable];
    return hideRoot ? (React.createElement("li", { ...styling('rootNode', ...stylingArgs) },
        React.createElement("ul", { ...styling('rootNodeChildren', ...stylingArgs) }, renderedChildren))) : (React.createElement("li", { ...styling('nestedNode', ...stylingArgs) },
        expandable && (React.createElement(JSONArrow, { styling: styling, nodeType: nodeType, expanded: expanded, onClick: handleClick })),
        React.createElement("label", { ...styling(['label', 'nestedNodeLabel'], ...stylingArgs), onClick: handleClick }, labelRenderer(...stylingArgs)),
        React.createElement("span", { ...styling('nestedNodeItemString', ...stylingArgs), onClick: handleClick }, renderedItemString),
        React.createElement("ul", { ...styling('nestedNodeChildren', ...stylingArgs) }, renderedChildren)));
}