UNPKG

mp-lens

Version:

微信小程序分析工具 (Unused Code, Dependencies, Visualization)

149 lines 8.01 kB
"use strict"; var __importDefault = (this && this.__importDefault) || function (mod) { return (mod && mod.__esModule) ? mod : { "default": mod }; }; Object.defineProperty(exports, "__esModule", { value: true }); exports.TreeView = TreeView; const jsx_runtime_1 = require("preact/jsx-runtime"); const hooks_1 = require("preact/hooks"); const TreeView_module_css_1 = __importDefault(require("./TreeView.module.css")); // Import CSS module // Recursive TreeNode component function TreeNode({ node, onNodeSelect, selectedNodeId, isExpanded, toggleNode, isNodeExpandedCheck, depth, // Current nesting depth }) { var _a; console.log('TreeNode depth', depth); const isSelected = node.id === selectedNodeId; const hasChildren = node.children && node.children.length > 0; const indentSize = 20; // Pixels per depth level const handleNodeClick = () => { onNodeSelect(node); }; // Renamed from handleToggleClick for clarity const handleNodeDoubleClick = (e) => { e.stopPropagation(); // Prevent potential text selection issues // Only toggle if the node actually has children if (hasChildren) { toggleNode(node.id); } }; // Add separate handler for triangle toggle click const handleToggleClick = (e) => { e.stopPropagation(); // Prevent the node selection if (hasChildren) { toggleNode(node.id); } }; return ((0, jsx_runtime_1.jsxs)("li", { children: [(0, jsx_runtime_1.jsxs)("div", { "data-node-id": node.id, onClick: handleNodeClick, onDblClick: handleNodeDoubleClick, className: `${TreeView_module_css_1.default.treeNodeItem} ${isSelected ? TreeView_module_css_1.default.selected : ''}`, title: `ID: ${node.id}`, style: { paddingLeft: `${depth * indentSize}px` }, children: [hasChildren && ( // Restore the onClick handler for the toggle span (0, jsx_runtime_1.jsx)("span", { className: TreeView_module_css_1.default.toggle, onClick: handleToggleClick, children: isExpanded ? '▼' : '▶' })), !hasChildren && (0, jsx_runtime_1.jsx)("span", { className: TreeView_module_css_1.default.toggle, children: "\u00A0" }), " ", (0, jsx_runtime_1.jsx)("span", { className: TreeView_module_css_1.default.label, children: node.label })] }), hasChildren && isExpanded && ((0, jsx_runtime_1.jsx)("ul", { children: (_a = node.children) === null || _a === void 0 ? void 0 : _a.map((child) => ((0, jsx_runtime_1.jsx)(TreeNode, { node: child, onNodeSelect: onNodeSelect, selectedNodeId: selectedNodeId, isExpanded: isNodeExpandedCheck(child.id), toggleNode: toggleNode, isNodeExpandedCheck: isNodeExpandedCheck, depth: depth + 1 }, child.id))) }))] })); } // Helper function to collect all expandable node IDs function getAllExpandableNodeIds(node) { const ids = new Set(); function traverse(currentNode) { if (currentNode.children && currentNode.children.length > 0) { ids.add(currentNode.id); currentNode.children.forEach(traverse); } } traverse(node); return ids; } // *** NEW: Helper function to find ancestor IDs *** function findAncestorIds(targetId, rootNode) { const path = []; function traverse(currentNode) { // Add current node to path temporarily path.push(currentNode.id); if (currentNode.id === targetId) { // Found the target, path is complete (excluding target itself) path.pop(); // Remove targetId from the path of ancestors return true; } if (currentNode.children) { for (const child of currentNode.children) { if (traverse(child)) { // Found in this subtree, keep path as is return true; } } } // Not found in this subtree, backtrack path.pop(); return false; } traverse(rootNode); return path; // Return the collected ancestor IDs } // Main TreeView component - manages expansion state function TreeView({ data, onNodeSelect, selectedNodeId, onExpandAll, onCollapseAll, }) { const [expandedNodes, setExpandedNodes] = (0, hooks_1.useState)(new Set([data.id])); // Calculate all expandable node IDs once const allExpandableIds = (0, hooks_1.useMemo)(() => getAllExpandableNodeIds(data), [data]); // *** useEffect to expand ancestors when selectedNodeId changes *** (0, hooks_1.useEffect)(() => { if (selectedNodeId && data) { // Find the path of ancestors for the selected node const ancestors = findAncestorIds(selectedNodeId, data); if (ancestors.length > 0) { setExpandedNodes((prevExpanded) => { const newExpanded = new Set(prevExpanded); // Add all ancestors to the set ancestors.forEach((id) => newExpanded.add(id)); // Avoid creating new set if no changes needed if (ancestors.every((id) => prevExpanded.has(id))) { return prevExpanded; } console.log('[TreeView] Expanding ancestors:', ancestors); return newExpanded; }); } } // Dependency: selectedNodeId (prop) and data (prop, unlikely to change but good practice) }, [selectedNodeId, data]); // Scroll to selected node when it changes (0, hooks_1.useEffect)(() => { if (selectedNodeId) { // Use a timeout to ensure the DOM has been updated after any potential expansions const timer = setTimeout(() => { const element = document.querySelector(`[data-node-id="${selectedNodeId}"]`); if (element) { element.scrollIntoView({ behavior: 'smooth', block: 'nearest', }); } }, 100); // A small delay is sometimes necessary return () => clearTimeout(timer); // Cleanup timeout } }, [selectedNodeId]); const toggleNode = (nodeId) => { setExpandedNodes((prev) => { const newSet = new Set(prev); if (newSet.has(nodeId)) { newSet.delete(nodeId); } else { newSet.add(nodeId); } return newSet; }); }; // Implement expand/collapse all logic using useCallback const handleExpandAll = (0, hooks_1.useCallback)(() => { setExpandedNodes(allExpandableIds); // Call external handler if provided (though maybe not needed if state managed here) if (onExpandAll) onExpandAll(); }, [allExpandableIds, onExpandAll]); const handleCollapseAll = (0, hooks_1.useCallback)(() => { setExpandedNodes(new Set([data.id])); // Keep root expanded // Call external handler if provided if (onCollapseAll) onCollapseAll(); }, [data.id, onCollapseAll]); // Helper function to pass down expansion state const isNodeExpanded = (nodeId) => expandedNodes.has(nodeId); return ((0, jsx_runtime_1.jsxs)("div", { className: TreeView_module_css_1.default.treeView, children: [(0, jsx_runtime_1.jsxs)("div", { className: TreeView_module_css_1.default.treeControls, children: [(0, jsx_runtime_1.jsx)("button", { onClick: handleExpandAll, children: "Expand All" }), (0, jsx_runtime_1.jsx)("button", { onClick: handleCollapseAll, children: "Collapse All" })] }), (0, jsx_runtime_1.jsx)("div", { className: TreeView_module_css_1.default.treeContainer, children: (0, jsx_runtime_1.jsx)("ul", { children: (0, jsx_runtime_1.jsx)(TreeNode, { node: data, onNodeSelect: onNodeSelect, selectedNodeId: selectedNodeId, isExpanded: isNodeExpanded(data.id), toggleNode: toggleNode, isNodeExpandedCheck: isNodeExpanded, depth: 0 }, data.id) }) })] })); } //# sourceMappingURL=TreeView.js.map