datastake-daf 0.6.773 → 0.6.774

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.
@@ -12465,6 +12465,8 @@ const Style$M = styled__default["default"].div`
12465
12465
  width: 100%;
12466
12466
  height: 472px;
12467
12467
 
12468
+
12469
+
12468
12470
  .filter-cont {
12469
12471
  position: absolute;
12470
12472
  top: 24px;
@@ -12567,11 +12569,24 @@ const Style$M = styled__default["default"].div`
12567
12569
  align-items: center;
12568
12570
  }
12569
12571
 
12570
- .marker-chain {
12571
- display: flex;
12572
- align-items: center;
12573
- justify-content: center;
12574
- }
12572
+ .marker-chain {
12573
+ display: flex;
12574
+ align-items: center;
12575
+ justify-content: center;
12576
+ }
12577
+
12578
+ .animated-polyline {
12579
+ stroke-dasharray: 10 10;
12580
+ animation: dash-flow 1.5s linear infinite;
12581
+ stroke-linecap: round;
12582
+ }
12583
+
12584
+ @keyframes dash-flow {
12585
+ to {
12586
+ stroke-dashoffset: -20;
12587
+ }
12588
+ }
12589
+
12575
12590
 
12576
12591
  }
12577
12592
 
@@ -13017,18 +13032,15 @@ const VILLAGE = "village";
13017
13032
  const EXPORTER = "exporter";
13018
13033
  const PROCESSOR = "mineralProcessor";
13019
13034
  const DEPOT = "depot";
13035
+ const OPERATOR = "miningOperator";
13020
13036
  const MAX_EXTRA_SMALL_ZOOM_THRESHOLD = 2;
13021
13037
  const MAX_SMALL_ZOOM_THRESHOLD = 3;
13022
13038
  const MAX_MEDIUM_ZOOM_THRESHOLD = 6;
13023
13039
  const LOCATION_TYPES = [MINE_SITE, VILLAGE];
13024
- const STAKEHOLDER_TYPES = [EXPORTER, PROCESSOR, DEPOT];
13040
+ const STAKEHOLDER_TYPES = [EXPORTER, PROCESSOR, DEPOT, OPERATOR];
13025
13041
  const RADIUS_SMALL = 15;
13026
13042
  const RADIUS_MEDIUM = 35;
13027
13043
  const RADIUS_LARGE = 60;
13028
- const RADIUS_CURVE_SMALL = 10;
13029
- const RADIUS_CURVE_MEDIUM = 15;
13030
- const RADIUS_CURVE_LARGE = 20;
13031
- const TENSION = 0.2;
13032
13044
  function isLocation(type) {
13033
13045
  return LOCATION_TYPES.includes(type);
13034
13046
  }
@@ -13085,7 +13097,6 @@ function getStakeholderPosition({
13085
13097
  const isLarge = isLargeMarker(zoom);
13086
13098
  let radius;
13087
13099
  let center = {
13088
- // NOT BEING USED FOR NOW AND MAYBE NEVER
13089
13100
  left: 0,
13090
13101
  top: 0
13091
13102
  };
@@ -13109,6 +13120,25 @@ function getStakeholderPosition({
13109
13120
  angleDeg
13110
13121
  };
13111
13122
  }
13123
+ function applyAnimationDirect(el, isShortLink) {
13124
+ if (!(el instanceof SVGElement) || isShortLink) return;
13125
+ el.style.strokeDasharray = "10, 10";
13126
+ el.style.strokeDashoffset = "0";
13127
+ el.style.animation = "dash-flow 1.2s linear infinite";
13128
+ el.classList.add('animated-polyline');
13129
+ }
13130
+ function removeAnimationFromElement(element) {
13131
+ if (!element) return;
13132
+ element.classList.remove('animated-polyline');
13133
+ element.style.animation = '';
13134
+ element.style.strokeDasharray = '';
13135
+ }
13136
+ function applyAnimationToPolyline(polyline, isShortLink) {
13137
+ const element = polyline.getElement();
13138
+ if (element) {
13139
+ applyAnimationDirect(element, isShortLink);
13140
+ }
13141
+ }
13112
13142
  function createPolyline({
13113
13143
  L,
13114
13144
  startLatLng,
@@ -13118,109 +13148,47 @@ function createPolyline({
13118
13148
  zoom,
13119
13149
  listOfPolylines = [],
13120
13150
  isFromStakeholder = false,
13121
- isForceOpen = false
13151
+ isForceOpen = false,
13152
+ stakeholderType = null,
13153
+ animated = false,
13154
+ mapRef
13122
13155
  }) {
13123
- const width = isFromStakeholder && isExtraSmallMarker(zoom) && !isForceOpen ? 0 : 1.2;
13124
- const coordinates = [[startLatLng.lat, startLatLng.lng], [endLatLng.lat, endLatLng.lng]];
13125
- const style = {
13156
+ const lineWidth = isFromStakeholder && isExtraSmallMarker(zoom) && !isForceOpen ? 0 : 1.2;
13157
+ const isShortLink = stakeholderType === OPERATOR || isFromStakeholder;
13158
+ const shouldAnimate = animated;
13159
+ const lineCoordinates = [[startLatLng.lat, startLatLng.lng], [endLatLng.lat, endLatLng.lng]];
13160
+ const polylineStyle = {
13126
13161
  color: "var(--base-gray-70)",
13127
- weight: width,
13128
- opacity: 0.5,
13129
- smoothFactor: 1,
13162
+ weight: lineWidth,
13163
+ opacity: isSelected ? 1 : 0.5,
13164
+ smoothFactor: 0,
13130
13165
  id,
13131
- dashArray: !isSelected ? "5, 5" : "0, 0"
13166
+ dashArray: isShortLink ? "0, 0" : shouldAnimate ? "10, 10" : !isSelected ? "5, 5" : "10, 10",
13167
+ renderer: L.svg()
13132
13168
  };
13133
- const newPolyline = L.polyline(coordinates, style);
13134
- if (listOfPolylines.find(p => p.options.id === id)) {
13135
- const polylineToUpdateCoordinates = listOfPolylines.find(p => p.options.id === id);
13136
- polylineToUpdateCoordinates.setLatLngs(coordinates);
13137
- polylineToUpdateCoordinates.setStyle(style);
13138
- } else {
13139
- listOfPolylines.push(newPolyline);
13140
- }
13141
- return newPolyline;
13142
- }
13143
- function createCurvePath({
13144
- zoom,
13145
- totalMarkers,
13146
- markerIndex
13147
- }) {
13148
- const radius = getCurvePointRadius(zoom);
13149
- const {
13150
- x,
13151
- y,
13152
- angleDeg
13153
- } = getAngleDeg(totalMarkers, markerIndex, radius);
13154
- return {
13155
- x,
13156
- y,
13157
- angleDeg
13158
- };
13159
- }
13160
- function getCurvePointRadius(zoom) {
13161
- const isSmall = isSmallMarker(zoom) || isExtraSmallMarker(zoom);
13162
- const isMedium = isMediumMarker(zoom);
13163
- if (isSmall) {
13164
- return RADIUS_SMALL + RADIUS_CURVE_SMALL;
13165
- } else if (isMedium) {
13166
- return RADIUS_MEDIUM + RADIUS_CURVE_MEDIUM;
13167
- } else {
13168
- return RADIUS_LARGE + RADIUS_CURVE_LARGE;
13169
- }
13170
- }
13171
- function buildSmoothCurve(layerPoints, mapRef) {
13172
- const path = [];
13173
- for (let i = 0; i < layerPoints.length - 1; i++) {
13174
- const p0 = layerPoints[i];
13175
- const p1 = layerPoints[i + 1];
13176
- const pPrev = layerPoints[i - 1] || p0;
13177
- const pNext = layerPoints[i + 2] || p1;
13178
- const cp1 = L__namespace.point(p0.x + (p1.x - pPrev.x) * TENSION, p0.y + (p1.y - pPrev.y) * TENSION);
13179
- const cp2 = L__namespace.point(p1.x - (pNext.x - p0.x) * TENSION, p1.y - (pNext.y - p0.y) * TENSION);
13180
- if (i === 0) {
13181
- path.push("M", [mapRef.layerPointToLatLng(p0).lat, mapRef.layerPointToLatLng(p0).lng]);
13169
+ const existingPolyline = listOfPolylines.find(p => p.options.id === id);
13170
+ if (existingPolyline) {
13171
+ removeAnimationFromElement(existingPolyline.getElement());
13172
+ existingPolyline.setLatLngs(lineCoordinates);
13173
+ existingPolyline.setStyle(polylineStyle);
13174
+ if (shouldAnimate && isSelected) {
13175
+ existingPolyline.once('add', () => {
13176
+ applyAnimationToPolyline(existingPolyline, isShortLink);
13177
+ });
13178
+ applyAnimationToPolyline(existingPolyline, isShortLink);
13182
13179
  }
13183
- path.push("C", [mapRef.layerPointToLatLng(cp1).lat, mapRef.layerPointToLatLng(cp1).lng], [mapRef.layerPointToLatLng(cp2).lat, mapRef.layerPointToLatLng(cp2).lng], [mapRef.layerPointToLatLng(p1).lat, mapRef.layerPointToLatLng(p1).lng]);
13180
+ return existingPolyline;
13184
13181
  }
13185
- return path;
13186
- }
13187
- function getSiblingCurveStrength(zoom) {
13188
- if (isExtraSmallMarker(zoom)) return RADIUS_CURVE_SMALL / 2;
13189
- if (isSmallMarker(zoom)) return RADIUS_CURVE_MEDIUM;
13190
- if (isMediumMarker(zoom)) return RADIUS_CURVE_LARGE;
13191
- return RADIUS_CURVE_LARGE;
13192
- }
13193
- function buildCurveWIthTwoSiblings({
13194
- mapRef,
13195
- startLatLng,
13196
- endLatLng,
13197
- zoom,
13198
- isSelected,
13199
- id
13200
- }) {
13201
- const fromPoint = mapRef.latLngToLayerPoint(startLatLng);
13202
- const toPoint = mapRef.latLngToLayerPoint(endLatLng);
13203
- const midX = (fromPoint.x + toPoint.x) / 2;
13204
- const midY = (fromPoint.y + toPoint.y) / 2 + (isSmallMarker(zoom) ? RADIUS_CURVE_SMALL / 2 : 0);
13205
- const dx = toPoint.x - fromPoint.x;
13206
- const dy = toPoint.y - fromPoint.y;
13207
- const normal = L__namespace.point(-dy, dx);
13208
- const length = Math.sqrt(normal.x ** 2 + normal.y ** 2) || 1;
13209
- const normalized = normal.multiplyBy(1 / length);
13210
- const curveStrength = getSiblingCurveStrength(zoom);
13211
- const controlPoint = L__namespace.point(midX, midY).add(normalized.multiplyBy(curveStrength));
13212
- const latlngs = [startLatLng, mapRef.layerPointToLatLng(controlPoint), endLatLng];
13213
- const layerPoints = latlngs.map(latlng => mapRef.latLngToLayerPoint(latlng));
13214
- const path = buildSmoothCurve(layerPoints, mapRef);
13215
- const curve = L__namespace.curve(path, {
13216
- color: "var(--base-gray-70)",
13217
- weight: isExtraSmallMarker(zoom) ? 0 : 1.2,
13218
- opacity: 0.5,
13219
- smoothFactor: 1,
13220
- id,
13221
- dashArray: !isSelected ? "5, 5" : "0, 0"
13222
- });
13223
- mapRef.addLayer(curve);
13182
+ const newPolyline = L.polyline(lineCoordinates, polylineStyle);
13183
+ newPolyline.addTo(mapRef);
13184
+ listOfPolylines.push(newPolyline);
13185
+ if (shouldAnimate && isSelected) {
13186
+ newPolyline.once('add', () => {
13187
+ applyAnimationToPolyline(newPolyline, isShortLink);
13188
+ });
13189
+ applyAnimationToPolyline(newPolyline, isShortLink);
13190
+ }
13191
+ return newPolyline;
13224
13192
  }
13225
13193
 
13226
13194
  const StakeholderMarker = styled__default["default"].div`
@@ -13522,6 +13490,9 @@ function StakeholderIcon$1({
13522
13490
  return null;
13523
13491
  }, [parentId, allData]);
13524
13492
  React.useEffect(() => {
13493
+ if (selectedMarkersId.length === 0 || !isSelected) {
13494
+ return;
13495
+ }
13525
13496
  linkNodesData.map(node => {
13526
13497
  const isConnectingToStakeholder = node.isStakeholder;
13527
13498
  const id = `${data.datastakeId}-${node.stakeholderId || node.datastakeId}`;
@@ -13533,8 +13504,6 @@ function StakeholderIcon$1({
13533
13504
  const stakeholderPoint = centerPoint.add(L__namespace.point(x, y));
13534
13505
  const stakeholderLatLng = mapRef.layerPointToLatLng(stakeholderPoint);
13535
13506
  let endLatLng = L__namespace.latLng(node.gps.latitude, node.gps.longitude);
13536
- const areNextToEachOther = targetMarkerIndex === index + 1 || targetMarkerIndex === index - 1 || index === 0 && targetMarkerIndex === node.totalStakeholders - 1 || targetMarkerIndex === 0 && index === node.totalStakeholders - 1;
13537
- const areOnlyTwoSiblings = node.totalStakeholders === 2;
13538
13507
  if (isExtraSmallMarker(zoom) && !isForceOpen) {
13539
13508
  createPolyline({
13540
13509
  L: L__namespace,
@@ -13544,7 +13513,8 @@ function StakeholderIcon$1({
13544
13513
  zoom,
13545
13514
  isSelected,
13546
13515
  id,
13547
- listOfPolylines: polylinesRef.current
13516
+ listOfPolylines: polylinesRef.current,
13517
+ animated: true
13548
13518
  });
13549
13519
  return;
13550
13520
  }
@@ -13562,61 +13532,8 @@ function StakeholderIcon$1({
13562
13532
  const nodePoint = mapRef.latLngToLayerPoint(nodeLatLng);
13563
13533
  const endPoint = L__namespace.point(x + nodePoint.x + center.left, y + nodePoint.y + center.top);
13564
13534
  endLatLng = mapRef.layerPointToLatLng(endPoint);
13565
- if (isSibling && (!areNextToEachOther || areOnlyTwoSiblings)) {
13566
- if (areOnlyTwoSiblings) {
13567
- buildCurveWIthTwoSiblings({
13568
- mapRef,
13569
- startLatLng: stakeholderLatLng,
13570
- endLatLng,
13571
- zoom,
13572
- isSelected,
13573
- id
13574
- });
13575
- return;
13576
- }
13577
- const total = node.totalStakeholders;
13578
- let from = index;
13579
- let to = targetMarkerIndex;
13580
- let flip = false;
13581
- const forwardDistance = (to - from + total) % total;
13582
- const backwardDistance = (from - to + total) % total;
13583
- if (backwardDistance < forwardDistance) {
13584
- [from, to] = [to, from];
13585
- flip = true;
13586
- }
13587
- const intermediateIndices = [];
13588
- for (let i = 1; i < (to - from + total) % total; i++) {
13589
- intermediateIndices.push((from + i) % total);
13590
- }
13591
- const indices = [from, ...intermediateIndices, to];
13592
- const intermediatePoints = [];
13593
- for (const i of indices) {
13594
- const {
13595
- x,
13596
- y
13597
- } = createCurvePath({
13598
- zoom,
13599
- totalMarkers: node.totalStakeholders,
13600
- markerIndex: i
13601
- });
13602
- const point = centerPoint.add(L__namespace.point(x, y));
13603
- const latlng = mapRef.layerPointToLatLng(point);
13604
- intermediatePoints.push(latlng);
13605
- }
13606
- const latlngs = flip ? [endLatLng, ...intermediatePoints, stakeholderLatLng] : [stakeholderLatLng, ...intermediatePoints, endLatLng];
13607
- const layerPoints = latlngs.map(latlng => mapRef.latLngToLayerPoint(latlng));
13608
- const path = buildSmoothCurve(layerPoints, mapRef);
13609
- const curve = L__namespace?.curve?.(path, {
13610
- color: "var(--base-gray-70)",
13611
- weight: isExtraSmallMarker(zoom) ? 0 : 1,
13612
- opacity: isSelected ? 1 : 0.5,
13613
- smoothFactor: 1,
13614
- id
13615
- });
13616
- mapRef.addLayer(curve);
13617
- return;
13618
- }
13619
13535
  }
13536
+ // Always use straight lines
13620
13537
  createPolyline({
13621
13538
  L: L__namespace,
13622
13539
  mapRef,
@@ -13626,10 +13543,11 @@ function StakeholderIcon$1({
13626
13543
  isFromStakeholder: false,
13627
13544
  isSelected,
13628
13545
  id,
13629
- listOfPolylines: polylinesRef.current
13546
+ listOfPolylines: polylinesRef.current,
13547
+ animated: true
13630
13548
  });
13631
13549
  });
13632
- }, [mapRef, x, y, parentData, linkNodesData, isSelected, zoom, isForceOpen]);
13550
+ }, [mapRef, x, y, parentData, linkNodesData, isSelected, zoom, isForceOpen, selectedMarkersId]);
13633
13551
  return /*#__PURE__*/jsxRuntime.jsx(jsxRuntime.Fragment, {
13634
13552
  children: /*#__PURE__*/jsxRuntime.jsx(antd.Popover, {
13635
13553
  content: renderTooltipJsx({
@@ -13696,6 +13614,8 @@ function LocationIcon({
13696
13614
  const linkedNodesData = React.useMemo(() => {
13697
13615
  const nodes = [];
13698
13616
  const links = data.links || [];
13617
+
13618
+ // Add links from the location itself
13699
13619
  links.forEach(link => {
13700
13620
  allData.forEach(d => {
13701
13621
  if (d.datastakeId === link) {
@@ -13715,8 +13635,45 @@ function LocationIcon({
13715
13635
  }
13716
13636
  });
13717
13637
  });
13638
+
13639
+ // ADD: Also include links from this location's stakeholders
13640
+ const stakeholders = data.stakeholders || [];
13641
+ stakeholders.forEach(stakeholder => {
13642
+ const stakeholderLinks = stakeholder.links || [];
13643
+ stakeholderLinks.forEach(link => {
13644
+ allData.forEach(d => {
13645
+ // Check if it's a direct location link
13646
+ if (d.datastakeId === link) {
13647
+ // Avoid duplicates
13648
+ if (!nodes.find(n => n.datastakeId === link && !n.isStakeholder)) {
13649
+ nodes.push({
13650
+ ...d,
13651
+ fromStakeholderId: stakeholder.datastakeId
13652
+ });
13653
+ }
13654
+ }
13655
+ // Check if it's a stakeholder link
13656
+ if (d.stakeholders && d.stakeholders.length > 0) {
13657
+ d.stakeholders.forEach(targetStakeholder => {
13658
+ if (targetStakeholder.datastakeId === link) {
13659
+ // Avoid duplicates
13660
+ if (!nodes.find(n => n.isStakeholder && n.datastakeId === d.datastakeId && n.stakeholdersIndex === d.stakeholders.indexOf(targetStakeholder))) {
13661
+ nodes.push({
13662
+ ...d,
13663
+ isStakeholder: true,
13664
+ totalStakeholders: d.stakeholders.length,
13665
+ stakeholdersIndex: d.stakeholders.indexOf(targetStakeholder),
13666
+ fromStakeholderId: stakeholder.datastakeId
13667
+ });
13668
+ }
13669
+ }
13670
+ });
13671
+ }
13672
+ });
13673
+ });
13674
+ });
13718
13675
  return nodes;
13719
- }, [JSON.stringify(allData), JSON.stringify(data.links), zoom]);
13676
+ }, [JSON.stringify(allData), JSON.stringify(data.links), JSON.stringify(data.stakeholders), zoom]);
13720
13677
  const stakeholdersOfLocation = React.useMemo(() => {
13721
13678
  return data?.stakeholders || [];
13722
13679
  }, [data.stakeholders, zoom]);
@@ -13734,7 +13691,13 @@ function LocationIcon({
13734
13691
  currentRoots.clear();
13735
13692
  markersRef.current = [];
13736
13693
 
13737
- // Create new markers
13694
+ // Only create stakeholder markers if this location or any of its stakeholders are selected
13695
+ const shouldShowStakeholders = isSelected || stakeholdersOfLocation.some(stk => selectedMarkersId.includes(stk.datastakeId));
13696
+ if (!shouldShowStakeholders || selectedMarkersId.length === 0) {
13697
+ return;
13698
+ }
13699
+
13700
+ // Create new markers only when selected
13738
13701
  stakeholdersOfLocation.forEach((stakeholder, index) => {
13739
13702
  const markerId = `${stakeholder.datastakeId}`;
13740
13703
  const {
@@ -13820,7 +13783,9 @@ function LocationIcon({
13820
13783
  zoom,
13821
13784
  isFromStakeholder: true,
13822
13785
  isForceOpen,
13823
- listOfPolylines: polylinesRef.current
13786
+ listOfPolylines: polylinesRef.current,
13787
+ stakeholderType: stakeholder.type,
13788
+ animated: true
13824
13789
  });
13825
13790
  });
13826
13791
  return () => {
@@ -13835,38 +13800,88 @@ function LocationIcon({
13835
13800
  rootsMapRef.current.clear();
13836
13801
  markersRef.current = [];
13837
13802
  };
13838
- }, [stakeholdersOfLocation, selectedMarkersId, activeMarker]);
13839
- linkedNodesData.map(node => {
13840
- const id = `${data.datastakeId}-${node.datastakeId}`;
13841
- const isConnectingToStakeholder = node.isStakeholder;
13842
- const centerLatLng = L__namespace.latLng(data.gps.latitude, data.gps.longitude);
13843
- let endLatLng = L__namespace.latLng(node.gps.latitude, node.gps.longitude);
13844
- const isConnectingToStakeholderSelected = selectedMarkersId.includes(node.datastakeId);
13845
- if (isConnectingToStakeholder && !isExtraSmallMarker(zoom)) {
13846
- const {
13847
- x,
13848
- y
13849
- } = getStakeholderPosition({
13803
+ }, [stakeholdersOfLocation, selectedMarkersId, activeMarker, zoom]);
13804
+
13805
+ // Only create polylines for linked nodes when something is selected
13806
+ React.useEffect(() => {
13807
+ if (selectedMarkersId.length === 0) {
13808
+ return;
13809
+ }
13810
+
13811
+ // IMPORTANT: Only draw links if this location is actually selected
13812
+ // Not just highlighted as part of the chain
13813
+ if (!isSelected) {
13814
+ return;
13815
+ }
13816
+
13817
+ // Filter linkedNodesData to only include nodes that are in the selected chain
13818
+ const relevantLinks = linkedNodesData.filter(node => {
13819
+ // Check if the target node (location) is in the selected markers
13820
+ const targetLocationInSelection = selectedMarkersId.includes(node.datastakeId);
13821
+
13822
+ // If connecting to a stakeholder, check if that stakeholder is selected
13823
+ if (node.isStakeholder) {
13824
+ const stakeholderInSelection = node.stakeholdersIndex !== undefined && selectedMarkersId.includes(node.datastakeId);
13825
+ return stakeholderInSelection;
13826
+ }
13827
+ return targetLocationInSelection;
13828
+ });
13829
+ relevantLinks.forEach(node => {
13830
+ const id = node.fromStakeholderId ? `${node.fromStakeholderId}-${node.datastakeId}` : `${data.datastakeId}-${node.datastakeId}`;
13831
+ const isConnectingToStakeholder = node.isStakeholder;
13832
+
13833
+ // If the link is from a stakeholder, start from the stakeholder position
13834
+ let startLatLng;
13835
+ if (node.fromStakeholderId) {
13836
+ // Find the stakeholder index in this location's stakeholders
13837
+ const stakeholderIndex = stakeholdersOfLocation.findIndex(s => s.datastakeId === node.fromStakeholderId);
13838
+ if (stakeholderIndex !== -1) {
13839
+ const {
13840
+ x,
13841
+ y
13842
+ } = getStakeholderPosition({
13843
+ zoom,
13844
+ totalMarkers: stakeholdersOfLocation.length,
13845
+ markerIndex: stakeholderIndex
13846
+ });
13847
+ const centerLatLng = L__namespace.latLng(data.gps.latitude, data.gps.longitude);
13848
+ const centerPoint = mapRef.latLngToLayerPoint(centerLatLng);
13849
+ const stakeholderPoint = centerPoint.add(L__namespace.point(x, y));
13850
+ startLatLng = mapRef.layerPointToLatLng(stakeholderPoint);
13851
+ } else {
13852
+ startLatLng = L__namespace.latLng(data.gps.latitude, data.gps.longitude);
13853
+ }
13854
+ } else {
13855
+ startLatLng = L__namespace.latLng(data.gps.latitude, data.gps.longitude);
13856
+ }
13857
+ let endLatLng = L__namespace.latLng(node.gps.latitude, node.gps.longitude);
13858
+ const isConnectingToStakeholderSelected = selectedMarkersId.includes(node.datastakeId);
13859
+ if (isConnectingToStakeholder && !isExtraSmallMarker(zoom)) {
13860
+ const {
13861
+ x,
13862
+ y
13863
+ } = getStakeholderPosition({
13864
+ zoom,
13865
+ totalMarkers: node.totalStakeholders,
13866
+ markerIndex: node.stakeholdersIndex
13867
+ });
13868
+ const nodeLatLng = L__namespace.latLng(node.gps.latitude, node.gps.longitude);
13869
+ const nodePoint = mapRef.latLngToLayerPoint(nodeLatLng);
13870
+ const endPoint = L__namespace.point(x + nodePoint.x, y + nodePoint.y);
13871
+ endLatLng = mapRef.layerPointToLatLng(endPoint);
13872
+ }
13873
+ createPolyline({
13874
+ L: L__namespace,
13875
+ mapRef,
13876
+ startLatLng,
13877
+ endLatLng,
13878
+ isSelected: isConnectingToStakeholderSelected,
13879
+ id,
13850
13880
  zoom,
13851
- totalMarkers: node.totalStakeholders,
13852
- markerIndex: node.stakeholdersIndex
13853
- });
13854
- const nodeLatLng = L__namespace.latLng(node.gps.latitude, node.gps.longitude);
13855
- const nodePoint = mapRef.latLngToLayerPoint(nodeLatLng);
13856
- const endPoint = L__namespace.point(x + nodePoint.x, y + nodePoint.y);
13857
- endLatLng = mapRef.layerPointToLatLng(endPoint);
13858
- }
13859
- createPolyline({
13860
- L: L__namespace,
13861
- mapRef,
13862
- startLatLng: centerLatLng,
13863
- endLatLng,
13864
- isSelected: isConnectingToStakeholderSelected,
13865
- id,
13866
- zoom,
13867
- listOfPolylines: polylinesRef.current
13881
+ listOfPolylines: polylinesRef.current
13882
+ });
13868
13883
  });
13869
- });
13884
+ }, [linkedNodesData, selectedMarkersId, zoom, stakeholdersOfLocation, isSelected]);
13870
13885
  return /*#__PURE__*/jsxRuntime.jsx(antd.Popover, {
13871
13886
  content: renderTooltipJsx({
13872
13887
  title: data.name,
@@ -14382,7 +14397,8 @@ function useMapHelper$1({
14382
14397
  link: link,
14383
14398
  onClickLink: onClickLink,
14384
14399
  activeStakeholder: activeStakeholder,
14385
- setActiveStakeholder: setActiveStakeholder
14400
+ setActiveStakeholder: setActiveStakeholder,
14401
+ mapRef: mapRef
14386
14402
  }));
14387
14403
  roots.current.push(root);
14388
14404
  } else if (type === "location") {
@@ -14587,7 +14603,8 @@ const useMap$1 = ({
14587
14603
  MAP_TOKEN
14588
14604
  } = useMapConfig({
14589
14605
  app,
14590
- isSatellite
14606
+ isSatellite,
14607
+ mapRef: container
14591
14608
  });
14592
14609
  const [initialMarkerSetIsDone, setInitialMarkerSetIsDone] = React.useState(false);
14593
14610
  const [mapCenter, setMapCenter] = React.useState([0, 0]);
@@ -14604,6 +14621,8 @@ const useMap$1 = ({
14604
14621
  const graph = new Map();
14605
14622
  const stakeToLoc = new Map();
14606
14623
  const nodeTypes = new Map();
14624
+
14625
+ // Build the graph
14607
14626
  for (const loc of data) {
14608
14627
  const locId = loc.datastakeId;
14609
14628
  nodeTypes.set(locId, loc.type);
@@ -14628,26 +14647,45 @@ const useMap$1 = ({
14628
14647
  }
14629
14648
  }
14630
14649
  const highlightTable = {};
14650
+
14651
+ // Perform BFS/DFS to find all connected nodes in the entire chain
14631
14652
  for (const [node] of graph) {
14632
14653
  const highlighted = new Set();
14633
- highlighted.add(node);
14634
- const nodeIsStakeholder = !isLocation(nodeTypes.get(node));
14635
- if (nodeIsStakeholder && stakeToLoc.has(node)) {
14636
- const parentLoc = stakeToLoc.get(node);
14637
- highlighted.add(parentLoc);
14638
- }
14639
- for (const neighbor of graph.get(node) || []) {
14640
- const neighborIsStakeholder = !isLocation(nodeTypes.get(neighbor));
14641
- if (neighborIsStakeholder && stakeToLoc.has(neighbor)) {
14642
- const neighborParent = stakeToLoc.get(neighbor);
14643
- if (isLocation(nodeTypes.get(node)) && neighborParent === node || nodeIsStakeholder && stakeToLoc.get(node) === neighborParent) {
14644
- highlighted.add(neighbor);
14645
- } else {
14654
+ const queue = [node];
14655
+ const visited = new Set([node]);
14656
+ while (queue.length > 0) {
14657
+ const current = queue.shift();
14658
+ highlighted.add(current);
14659
+
14660
+ // Add parent location if current is stakeholder
14661
+ const currentIsStakeholder = !isLocation(nodeTypes.get(current));
14662
+ if (currentIsStakeholder && stakeToLoc.has(current)) {
14663
+ const parentLoc = stakeToLoc.get(current);
14664
+ if (!visited.has(parentLoc)) {
14665
+ highlighted.add(parentLoc);
14666
+ visited.add(parentLoc);
14667
+ queue.push(parentLoc);
14668
+ }
14669
+ }
14670
+
14671
+ // Traverse all neighbors
14672
+ for (const neighbor of graph.get(current) || []) {
14673
+ if (!visited.has(neighbor)) {
14674
+ visited.add(neighbor);
14675
+ queue.push(neighbor);
14646
14676
  highlighted.add(neighbor);
14647
- highlighted.add(neighborParent);
14677
+
14678
+ // If neighbor is stakeholder, add its parent location
14679
+ const neighborIsStakeholder = !isLocation(nodeTypes.get(neighbor));
14680
+ if (neighborIsStakeholder && stakeToLoc.has(neighbor)) {
14681
+ const neighborParent = stakeToLoc.get(neighbor);
14682
+ if (!visited.has(neighborParent)) {
14683
+ highlighted.add(neighborParent);
14684
+ visited.add(neighborParent);
14685
+ queue.push(neighborParent);
14686
+ }
14687
+ }
14648
14688
  }
14649
- } else {
14650
- highlighted.add(neighbor);
14651
14689
  }
14652
14690
  }
14653
14691
  highlightTable[node] = [...highlighted];
@@ -14712,19 +14750,29 @@ const useMap$1 = ({
14712
14750
  });
14713
14751
  }
14714
14752
  }
14753
+ if (type === "chain" && selectedMarkersId.length === 0) {
14754
+ if (polylinesRef.current.length) {
14755
+ polylinesRef.current.forEach(polyline => {
14756
+ if (mapRef.hasLayer(polyline)) {
14757
+ mapRef.removeLayer(polyline);
14758
+ }
14759
+ });
14760
+ polylinesRef.current = [];
14761
+ }
14762
+ }
14715
14763
  clearMapMarkers();
14716
14764
  if (data) {
14717
- // Filters out locations that are not connected to any stakeholders
14718
- const excludedType = ['village', 'town', 'area', 'territory'];
14719
- const filteredData = data?.filter(obj => !excludedType.includes(obj?.type) && (obj?.stakeholders?.length > 0 || data.some(other => other.datastakeId !== obj.datastakeId && (other.stakeholders || []).some(stk => (stk.links || []).includes(obj.datastakeId)))));
14765
+ const filteredData = data?.filter(obj => obj.type === 'mineSite' || obj?.stakeholders?.length > 0 || data.some(other => other.datastakeId !== obj.datastakeId && (other.stakeholders || []).some(stk => (stk.links || []).includes(obj.datastakeId))));
14720
14766
  const maxTotal = Math.max(...(data || []).map(d => d.total));
14721
14767
  const dataToRender = type === "chain" ? filteredData : data;
14722
14768
  dataToRender.forEach((d, i) => {
14723
14769
  addIconToMapInitialy([d?.marker?.lat, d?.marker?.lng], "location", d.category || "mineSite", d, maxTotal, i);
14724
14770
  });
14725
- polylinesRef.current.forEach(polyline => {
14726
- mapRef.addLayer(polyline);
14727
- });
14771
+ if (selectedMarkersId.length > 0) {
14772
+ polylinesRef.current.forEach(polyline => {
14773
+ mapRef.addLayer(polyline);
14774
+ });
14775
+ }
14728
14776
  mapRef.invalidateSize();
14729
14777
  mapRef.fire("moveend");
14730
14778
  }