@2112-lab/central-plant 0.2.10 → 0.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -541,6 +541,103 @@ var PathfindingManager = /*#__PURE__*/function (_BaseDisposable) {
541
541
  return this.pathDataStore.get(pathId);
542
542
  }
543
543
 
544
+ /**
545
+ * Propagate flowAttributes from the original connection list to any gateway-split
546
+ * rendered sub-paths in pathDataStore, then apply all flow visualizations.
547
+ * Called after every pathfinding execution (initial load and transform updates).
548
+ *
549
+ * @param {Array} connections - Original connections array (may include flowAttributes)
550
+ * @param {object} pathfindingResult - Result returned by _executePathfinding
551
+ * @private
552
+ */
553
+ }, {
554
+ key: "_propagateFlowAttributesAndApplyVisualizations",
555
+ value: function _propagateFlowAttributesAndApplyVisualizations(connections, pathfindingResult) {
556
+ var _this5 = this,
557
+ _this$sceneViewer;
558
+ if (!Array.isArray(connections) || !pathfindingResult) return;
559
+
560
+ // Pass 1: use the explicit gateway connection mappings to build a precise
561
+ // original-pathId → Set<renderedPathId> map.
562
+ var originalToSubPaths = new Map();
563
+ if (pathfindingResult.gateways) {
564
+ pathfindingResult.gateways.forEach(function (gateway) {
565
+ var _ref = gateway.connections || {},
566
+ removed = _ref.removed,
567
+ added = _ref.added;
568
+ if (!(removed !== null && removed !== void 0 && removed.length) || !(added !== null && added !== void 0 && added.length)) return;
569
+ removed.forEach(function (removedConn) {
570
+ var origId = "".concat(removedConn.from, "-->").concat(removedConn.to);
571
+ if (!originalToSubPaths.has(origId)) originalToSubPaths.set(origId, new Set());
572
+ added.forEach(function (addedConn) {
573
+ originalToSubPaths.get(origId).add("".concat(addedConn.from, "-->").concat(addedConn.to));
574
+ });
575
+ });
576
+ });
577
+ }
578
+ connections.forEach(function (conn) {
579
+ if (!conn.flowAttributes) return;
580
+ var origId = "".concat(conn.from, "-->").concat(conn.to);
581
+ var subPathIds = new Set(originalToSubPaths.get(origId) || []);
582
+ subPathIds.add(origId);
583
+ subPathIds.forEach(function (subPathId) {
584
+ var pd = _this5.pathDataStore.get(subPathId);
585
+ if (pd && Object.keys(pd.flowAttributes).length === 0) {
586
+ Object.entries(conn.flowAttributes).forEach(function (_ref2) {
587
+ var _ref3 = _rollupPluginBabelHelpers.slicedToArray(_ref2, 2),
588
+ key = _ref3[0],
589
+ value = _ref3[1];
590
+ return pd.setFlowAttribute(key, value);
591
+ });
592
+ }
593
+ });
594
+ });
595
+
596
+ // Pass 2: endpoint fallback for Gateway→Gateway intermediate segments and
597
+ // for paths whose connections were restructured by manualizeSegment/manualizeGateway.
598
+ // After manualization, currentSceneData.connections no longer contains the original
599
+ // A→B entry with flowAttributes (it's been split into new sub-connections), so we
600
+ // seed the endpoint maps from both the connections array AND from existing pathDataStore
601
+ // entries that already carry flowAttributes — those persist across re-executions.
602
+ var fromEndpointAttrs = new Map();
603
+ var toEndpointAttrs = new Map();
604
+
605
+ // Seed from persisted pathDataStore entries first (covers post-manualization re-runs)
606
+ this.pathDataStore.forEach(function (pd, pathId) {
607
+ if (Object.keys(pd.flowAttributes).length === 0) return;
608
+ var sepIdx = pathId.indexOf('-->');
609
+ if (sepIdx === -1) return;
610
+ var from = pathId.slice(0, sepIdx);
611
+ var to = pathId.slice(sepIdx + 3);
612
+ if (!fromEndpointAttrs.has(from)) fromEndpointAttrs.set(from, pd.flowAttributes);
613
+ if (!toEndpointAttrs.has(to)) toEndpointAttrs.set(to, pd.flowAttributes);
614
+ });
615
+
616
+ // Also seed from connections array (covers initial load before pathDataStore has any attrs)
617
+ connections.forEach(function (conn) {
618
+ if (!conn.flowAttributes) return;
619
+ if (!fromEndpointAttrs.has(conn.from)) fromEndpointAttrs.set(conn.from, conn.flowAttributes);
620
+ if (!toEndpointAttrs.has(conn.to)) toEndpointAttrs.set(conn.to, conn.flowAttributes);
621
+ });
622
+ this.pathDataStore.forEach(function (pd, pathId) {
623
+ if (Object.keys(pd.flowAttributes).length > 0) return;
624
+ var sepIdx = pathId.indexOf('-->');
625
+ if (sepIdx === -1) return;
626
+ var from = pathId.slice(0, sepIdx);
627
+ var to = pathId.slice(sepIdx + 3);
628
+ var attrs = fromEndpointAttrs.get(from) || toEndpointAttrs.get(to);
629
+ if (attrs) Object.entries(attrs).forEach(function (_ref4) {
630
+ var _ref5 = _rollupPluginBabelHelpers.slicedToArray(_ref4, 2),
631
+ key = _ref5[0],
632
+ value = _ref5[1];
633
+ return pd.setFlowAttribute(key, value);
634
+ });
635
+ });
636
+
637
+ // Apply visualizations
638
+ (_this$sceneViewer = this.sceneViewer) === null || _this$sceneViewer === void 0 || (_this$sceneViewer = _this$sceneViewer.managers) === null || _this$sceneViewer === void 0 || (_this$sceneViewer = _this$sceneViewer.pathFlowManager) === null || _this$sceneViewer === void 0 || _this$sceneViewer.applyAllVisualizations();
639
+ }
640
+
544
641
  /**
545
642
  * Initialize pathfinder and create paths
546
643
  */
@@ -548,9 +645,8 @@ var PathfindingManager = /*#__PURE__*/function (_BaseDisposable) {
548
645
  key: "initializePathfinder",
549
646
  value: (function () {
550
647
  var _initializePathfinder = _rollupPluginBabelHelpers.asyncToGenerator(/*#__PURE__*/_rollupPluginBabelHelpers.regenerator().m(function _callee2(data, crosscubeTextureSet) {
551
- var _this5 = this,
552
- _this$sceneViewer;
553
- var pathfindingResult, originalToSubPaths, fromEndpointAttrs, flowMgr;
648
+ var _this6 = this;
649
+ var pathfindingResult;
554
650
  return _rollupPluginBabelHelpers.regenerator().w(function (_context2) {
555
651
  while (1) switch (_context2.n) {
556
652
  case 0:
@@ -563,11 +659,11 @@ var PathfindingManager = /*#__PURE__*/function (_BaseDisposable) {
563
659
  data.connections.forEach(function (conn) {
564
660
  if (conn.flowAttributes && _rollupPluginBabelHelpers["typeof"](conn.flowAttributes) === 'object') {
565
661
  var pathId = "".concat(conn.from, "-->").concat(conn.to);
566
- var pd = _this5._getOrCreatePathData(pathId, conn.from, conn.to);
567
- Object.entries(conn.flowAttributes).forEach(function (_ref) {
568
- var _ref2 = _rollupPluginBabelHelpers.slicedToArray(_ref, 2),
569
- key = _ref2[0],
570
- value = _ref2[1];
662
+ var pd = _this6._getOrCreatePathData(pathId, conn.from, conn.to);
663
+ Object.entries(conn.flowAttributes).forEach(function (_ref6) {
664
+ var _ref7 = _rollupPluginBabelHelpers.slicedToArray(_ref6, 2),
665
+ key = _ref7[0],
666
+ value = _ref7[1];
571
667
  pd.setFlowAttribute(key, value);
572
668
  });
573
669
  console.log("\uD83C\uDF0A Loaded flowAttributes for path \"".concat(pathId, "\":"), conn.flowAttributes);
@@ -583,82 +679,7 @@ var PathfindingManager = /*#__PURE__*/function (_BaseDisposable) {
583
679
  });
584
680
  case 1:
585
681
  pathfindingResult = _context2.v;
586
- // ── Propagate flowAttributes to gateway-split rendered paths ──────────
587
- // The pathfinder may split a connection A→B through gateway waypoints,
588
- // producing sub-paths like A→G and G→B with different pathIds.
589
- // We need to copy the original connection's flowAttributes onto every
590
- // rendered sub-path entry in pathDataStore so the visualisation can
591
- // find them by their rendered pathId.
592
- if (Array.isArray(data.connections) && pathfindingResult) {
593
- // Pass 1: use the explicit gateway connection mappings to get a precise
594
- // original→sub-path map.
595
- originalToSubPaths = new Map(); // origPathId → Set<renderedPathId>
596
- if (pathfindingResult.gateways) {
597
- pathfindingResult.gateways.forEach(function (gateway) {
598
- var _ref3 = gateway.connections || {},
599
- removed = _ref3.removed,
600
- added = _ref3.added;
601
- if (!(removed !== null && removed !== void 0 && removed.length) || !(added !== null && added !== void 0 && added.length)) return;
602
- removed.forEach(function (removedConn) {
603
- var origId = "".concat(removedConn.from, "-->").concat(removedConn.to);
604
- if (!originalToSubPaths.has(origId)) originalToSubPaths.set(origId, new Set());
605
- added.forEach(function (addedConn) {
606
- originalToSubPaths.get(origId).add("".concat(addedConn.from, "-->").concat(addedConn.to));
607
- });
608
- });
609
- });
610
- }
611
- data.connections.forEach(function (conn) {
612
- if (!conn.flowAttributes) return;
613
- var origId = "".concat(conn.from, "-->").concat(conn.to);
614
- var subPathIds = new Set(originalToSubPaths.get(origId) || []);
615
- subPathIds.add(origId); // include the direct path if it wasn't rewired
616
-
617
- subPathIds.forEach(function (subPathId) {
618
- var pd = _this5.pathDataStore.get(subPathId);
619
- if (pd && Object.keys(pd.flowAttributes).length === 0) {
620
- Object.entries(conn.flowAttributes).forEach(function (_ref4) {
621
- var _ref5 = _rollupPluginBabelHelpers.slicedToArray(_ref4, 2),
622
- key = _ref5[0],
623
- value = _ref5[1];
624
- pd.setFlowAttribute(key, value);
625
- });
626
- console.log("\uD83C\uDF0A Propagated flowAttributes to sub-path \"".concat(subPathId, "\" from \"").concat(origId, "\""));
627
- }
628
- });
629
- });
630
-
631
- // Pass 2: endpoint fallback for any rendered path still missing attributes
632
- // (covers Gateway→Gateway intermediate segments not captured by gateway.connections.added)
633
- fromEndpointAttrs = new Map(); // connectorId → flowAttributes
634
- data.connections.forEach(function (conn) {
635
- if (conn.flowAttributes && !fromEndpointAttrs.has(conn.from)) {
636
- fromEndpointAttrs.set(conn.from, conn.flowAttributes);
637
- }
638
- });
639
- this.pathDataStore.forEach(function (pd, pathId) {
640
- if (Object.keys(pd.flowAttributes).length > 0) return;
641
- var sepIdx = pathId.indexOf('-->');
642
- if (sepIdx === -1) return;
643
- var from = pathId.slice(0, sepIdx);
644
- var attrs = fromEndpointAttrs.get(from);
645
- if (attrs) {
646
- Object.entries(attrs).forEach(function (_ref6) {
647
- var _ref7 = _rollupPluginBabelHelpers.slicedToArray(_ref6, 2),
648
- key = _ref7[0],
649
- value = _ref7[1];
650
- return pd.setFlowAttribute(key, value);
651
- });
652
- console.log("\uD83C\uDF0A Endpoint-matched flowAttributes for path \"".concat(pathId, "\""));
653
- }
654
- });
655
- }
656
-
657
- // ── Apply flow visualizations now that paths are rendered ──────────────
658
- flowMgr = (_this$sceneViewer = this.sceneViewer) === null || _this$sceneViewer === void 0 || (_this$sceneViewer = _this$sceneViewer.managers) === null || _this$sceneViewer === void 0 ? void 0 : _this$sceneViewer.pathFlowManager;
659
- if (flowMgr) {
660
- flowMgr.applyAllVisualizations();
661
- }
682
+ this._propagateFlowAttributesAndApplyVisualizations(data.connections, pathfindingResult);
662
683
 
663
684
  // Update connections with rewired connections
664
685
  if (pathfindingResult.rewiredConnections) {
@@ -784,6 +805,9 @@ var PathfindingManager = /*#__PURE__*/function (_BaseDisposable) {
784
805
  });
785
806
  case 2:
786
807
  result = _context3.v;
808
+ // Re-apply flow attribute colors (new materials are created on each execution)
809
+ this._propagateFlowAttributesAndApplyVisualizations(currentSceneData.connections, result);
810
+
787
811
  // Cache fingerprint + result for next comparison
788
812
  this._lastPathfindingFingerprint = fingerprint;
789
813
  this._lastPathfindingResult = result;
@@ -1771,7 +1771,7 @@ var SceneOperationsManager = /*#__PURE__*/function () {
1771
1771
  if (typeof window !== 'undefined') {
1772
1772
  isDev = window.location.hostname === 'localhost' || window.location.hostname === '127.0.0.1';
1773
1773
  }
1774
- if (isDev && segment.material) {
1774
+ if (isDev && process.env.DISABLE_MANUALIZED_SEGMENT_COLORING !== 'true' && segment.material) {
1775
1775
  segment.material.color.setHex(0x0000ff); // Blue
1776
1776
  console.log('🎨 Set manual segment material color to blue (dev mode)');
1777
1777
  }
@@ -1802,7 +1802,7 @@ var SceneOperationsManager = /*#__PURE__*/function () {
1802
1802
  console.log('🔌 Created connectors:', connectors);
1803
1803
 
1804
1804
  // In dev mode, enlarge connectors by 1.5x and turn them red
1805
- if (isDev) {
1805
+ if (isDev && process.env.DISABLE_MANUALIZED_SEGMENT_COLORING !== 'true') {
1806
1806
  connectors.forEach(function (connector) {
1807
1807
  if (connector) {
1808
1808
  connector.scale.set(1.25, 1.25, 1.25);
@@ -31,7 +31,7 @@ var CentralPlant = /*#__PURE__*/function (_BaseDisposable) {
31
31
  * Initialize the CentralPlant manager
32
32
  *
33
33
  * @constructor
34
- * @version 0.2.10
34
+ * @version 0.3.0
35
35
  * @updated 2025-10-22
36
36
  *
37
37
  * @description Creates a new CentralPlant instance and initializes internal managers and utilities.
@@ -25,7 +25,10 @@ export { loadTextureSetAndCreateMaterial } from './managers/environment/textureC
25
25
  export { ThreeJSResourceManager } from './managers/system/threeJSResourceManager.js';
26
26
  export { PerformanceMonitorManager } from './managers/system/performanceMonitorManager.js';
27
27
  export { OperationHistoryManager } from './managers/system/operationHistoryManager.js';
28
- export { CACHE_EXPIRY, CACHE_NAME_PREFIX, CacheManager, cacheManager } from './managers/CacheManager.js';
28
+ export { CACHE_EXPIRY, CACHE_NAME_PREFIX, CacheManager, cacheManager } from './managers/cache/CacheManager.js';
29
+ export { GLOBAL_CACHE_NAME, cacheJsonData, cleanExpiredCache, cleanInvalidCacheEntries, clearS3Cache, formatCacheExpiry, getAllCacheKeys, getCacheExpiryForPath, getCacheStats, getCachedJsonData, getCachedLocalFile, getCachedLocalFileURL, getCachedLocalJson, getCachedS3Json, getCachedS3Object, getCachedS3ObjectURL, getCurrentCacheName, getGlobalCacheStats, getGlobalOnlyCacheStats, getThumbnailKey, getUserOnlyCacheStats, isCached, isThumbnailCached, preloadLocalFiles, preloadS3Objects, removeCachedJsonData, resetCacheIdentity, resetGlobalCacheStats, switchCachePartition } from './managers/cache/S3CacheService.js';
30
+ export { S3MetadataCacheService, s3MetadataCache } from './managers/cache/S3MetadataCacheService.js';
31
+ export { measureS3Transfer } from './managers/cache/s3Timing.js';
29
32
  export { ModelManager } from './managers/scene/modelManager.js';
30
33
  export { default as modelPreloader } from './rendering/modelPreloader.js';
31
34
  import * as rendering2D from './rendering/rendering2D.js';