@mint-ui/map 1.2.0-test.65 → 1.2.0-test.67

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.
package/dist/index.es.js CHANGED
@@ -3951,32 +3951,26 @@ var CanvasMarkerLayer = function (props) {
3951
3951
 
3952
3952
  var _d = hasRenderEvent && 'renderEvent' in props ? props : {
3953
3953
  disableInteraction: false,
3954
- enableMultiSelect: false,
3955
3954
  onClick: undefined,
3956
3955
  onMouseOut: undefined,
3957
3956
  onMouseOver: undefined,
3958
3957
  renderEvent: undefined,
3959
3958
  selectedItem: undefined,
3960
3959
  selectedItems: undefined,
3961
- topOnHover: false,
3962
3960
  topStageZIndex: undefined
3963
3961
  },
3964
3962
  _e = _d.disableInteraction,
3965
3963
  disableInteraction = _e === void 0 ? false : _e,
3966
- _f = _d.enableMultiSelect,
3967
- enableMultiSelect = _f === void 0 ? false : _f,
3968
3964
  onClick = _d.onClick,
3969
3965
  onMouseOut = _d.onMouseOut,
3970
3966
  onMouseOver = _d.onMouseOver,
3971
3967
  renderEvent = _d.renderEvent,
3972
3968
  externalSelectedItem = _d.selectedItem,
3973
3969
  externalSelectedItems = _d.selectedItems,
3974
- rawTopStageZIndex = _d.topStageZIndex,
3975
- _g = _d.topOnHover,
3976
- topOnHover = _g === void 0 ? false : _g; // topOnHover가 false이거나 없으면 topStageZIndex를 사용하지 못하도록 제한
3970
+ rawTopStageZIndex = _d.topStageZIndex; // topStageZIndex가 있으면 hover 최상단 표시 활성화, 없으면 비활성화 (성능 우선)
3977
3971
 
3978
3972
 
3979
- var topStageZIndex = topOnHover && rawTopStageZIndex !== undefined ? rawTopStageZIndex : undefined;
3973
+ var topStageZIndex = rawTopStageZIndex;
3980
3974
  var controller = useMintMapController();
3981
3975
  var context = useCanvasContext();
3982
3976
  var currentZIndex = options.zIndex !== undefined ? options.zIndex : 0; // DOM Refs
@@ -4081,49 +4075,20 @@ var CanvasMarkerLayer = function (props) {
4081
4075
  name: 'base-render-shape',
4082
4076
  perfectDrawEnabled: false,
4083
4077
  sceneFunc: function (konvaContext) {
4084
- var ctx = konvaContext;
4085
- var hovered = hoveredItemRef.current; // 뷰포트 컬링: 화면에 보이는 항목만 필터링
4078
+ var ctx = konvaContext; // 뷰포트 컬링: 화면에 보이는 항목만 필터링
4086
4079
 
4087
4080
  var visibleItems = enableViewportCullingRef.current ? dataRef.current.filter(function (item) {
4088
4081
  return isInViewport$1(item);
4089
- }) : dataRef.current; // topStageZIndex가 설정되고 topOnHover가 true인 경우 hover된 항목은 Top Layer에서 처리
4090
- // topOnHover 옵션: hover된 항목을 나중에 그려서 최상위에 표시
4091
-
4092
- if (topStageZIndex !== undefined && topOnHover && hovered) {
4093
- visibleItems = visibleItems.filter(function (item) {
4094
- return item.id !== hovered.id;
4095
- });
4096
- } else if (topOnHover && !renderEvent && hovered) {
4097
- visibleItems = visibleItems.filter(function (item) {
4098
- return item.id !== hovered.id;
4099
- });
4100
- } // 일반 항목들 먼저 렌더링
4101
- // topOnHover가 false이고 renderEvent가 있으면 선택된 항목도 Base Layer에서 렌더링
4102
- // (Event Layer에서 선택된 항목을 렌더링하지 않으므로)
4103
- // topOnHover가 true이거나 renderEvent가 없으면 선택된 항목은 Base Layer에서 스킵됨
4104
-
4082
+ }) : dataRef.current; // Base Layer는 기본 마커만 렌더링 (hover된 항목도 포함)
4083
+ // hover 스타일은 Event Layer와 Top Layer에서 덧그려짐
4105
4084
 
4106
- var baseSelectedIds = !topOnHover && renderEvent ? selectedIdsRef.current : new Set();
4107
4085
  renderBase({
4108
4086
  ctx: ctx,
4109
- hoveredItem: hovered,
4087
+ hoveredItem: null,
4110
4088
  items: visibleItems,
4111
- selectedIds: baseSelectedIds,
4089
+ selectedIds: new Set(),
4112
4090
  utils: renderUtils
4113
- }); // topStageZIndex가 설정된 경우 hover된 항목은 Top Layer에서 처리하므로 여기서는 스킵
4114
- // hover된 항목을 마지막에 렌더링하여 최상위에 표시
4115
-
4116
- if (topStageZIndex === undefined && topOnHover && !renderEvent && hovered) {
4117
- if (!enableViewportCullingRef.current || isInViewport$1(hovered)) {
4118
- renderBase({
4119
- ctx: ctx,
4120
- hoveredItem: hovered,
4121
- items: [hovered],
4122
- selectedIds: selectedIdsRef.current,
4123
- utils: renderUtils
4124
- });
4125
- }
4126
- }
4091
+ });
4127
4092
  }
4128
4093
  });
4129
4094
  layer.add(shape);
@@ -4147,67 +4112,30 @@ var CanvasMarkerLayer = function (props) {
4147
4112
  sceneFunc: function (konvaContext) {
4148
4113
  var ctx = konvaContext;
4149
4114
  var selectedItems = mapValuesToArray(selectedItemsMapRef.current);
4150
- var hovered = hoveredItemRef.current; // topStageZIndex가 설정되고 topOnHover가 true이면 hover된 항목은 Top Layer에서 처리
4151
- // event 레이어에서는 hover된 항목을 완전히 제외하고 선택된 항목만 렌더링
4152
-
4153
- if (topStageZIndex !== undefined && topOnHover && hovered) {
4154
- // hover된 항목을 제외한 선택된 항목들
4155
- var selectedItemsWithoutHovered = selectedItems.filter(function (item) {
4156
- return item.id !== hovered.id;
4157
- }); // 선택된 항목만 그리기 (hover된 항목은 Top Layer에서 처리)
4158
-
4159
- renderEvent({
4160
- ctx: ctx,
4161
- hoveredItem: null,
4162
- selectedItem: selectedItemRef.current,
4163
- selectedItems: selectedItemsWithoutHovered,
4164
- topOnHover: topOnHover,
4165
- utils: renderUtils
4166
- });
4167
- } else if (topOnHover && hovered) {
4168
- renderEvent({
4169
- ctx: ctx,
4170
- hoveredItem: null,
4171
- selectedItem: selectedItemRef.current,
4172
- selectedItems: selectedItems.filter(function (item) {
4173
- return item.id !== hovered.id;
4174
- }),
4175
- topOnHover: topOnHover,
4176
- utils: renderUtils
4177
- });
4115
+ var hovered = hoveredItemRef.current; // selectedItem이 있으면 selectedItems 배열에 포함 (renderMarkerEvent가 selectedItems만 사용하므로)
4178
4116
 
4179
- if (!enableViewportCullingRef.current || isInViewport$1(hovered)) {
4180
- var hoveredIsSelected = selectedItems.some(function (item) {
4181
- return item.id === hovered.id;
4182
- });
4183
- var hoverSelectedItems = hoveredIsSelected ? [hovered] : [];
4184
- renderEvent({
4185
- ctx: ctx,
4186
- hoveredItem: hovered,
4187
- selectedItem: selectedItemRef.current,
4188
- selectedItems: hoverSelectedItems,
4189
- topOnHover: topOnHover,
4190
- utils: renderUtils
4191
- });
4117
+ if (selectedItemRef.current) {
4118
+ // selectedItem이 이미 selectedItems 포함되어 있지 않으면 추가
4119
+ var selectedItemId_1 = selectedItemRef.current.id;
4120
+
4121
+ if (!selectedItems.some(function (item) {
4122
+ return item.id === selectedItemId_1;
4123
+ })) {
4124
+ selectedItems = __spreadArray(__spreadArray([], selectedItems, true), [selectedItemRef.current], false);
4192
4125
  }
4193
- } else {
4194
- // topOnHoverfalse일 때는 hover된 항목을 나중에 그리지 않음
4195
- // 하지만 hover 스타일은 적용해야 하므로, hover 항목이 selectedItems에 포함되어 있지 않으면 추가
4196
- // renderEvent 함수에 topOnHover 정보를 전달하여,
4197
- // renderEvent 함수 내부에서 topOnHover가 false일 때는 hover된 항목을 마지막에 그리지 않도록 함
4198
- var hoveredIsSelected = hovered ? selectedItems.some(function (item) {
4199
- return item.id === hovered.id;
4200
- }) : false;
4201
- var finalSelectedItems = hovered && !hoveredIsSelected && !topOnHover ? __spreadArray(__spreadArray([], selectedItems, true), [hovered], false) : selectedItems;
4202
- renderEvent({
4203
- ctx: ctx,
4204
- hoveredItem: hovered,
4205
- selectedItem: selectedItemRef.current,
4206
- selectedItems: finalSelectedItems,
4207
- topOnHover: topOnHover,
4208
- utils: renderUtils
4209
- });
4210
- }
4126
+ } // Event Layer는 hover 효과 및 선택 상태를 덧그림
4127
+ // topStageZIndex있으면 hover된 항목은 Top Stage에서도 처리되지만,
4128
+ // Event Layer에서도 hover 스타일을 덧그려서 Base Layer 위에 표시됨
4129
+
4130
+
4131
+ renderEvent({
4132
+ ctx: ctx,
4133
+ hasTopStage: topStageZIndex !== undefined,
4134
+ hoveredItem: hovered,
4135
+ selectedItem: selectedItemRef.current,
4136
+ selectedItems: selectedItems,
4137
+ utils: renderUtils
4138
+ });
4211
4139
  }
4212
4140
  });
4213
4141
  layer.add(shape);
@@ -4220,7 +4148,7 @@ var CanvasMarkerLayer = function (props) {
4220
4148
  var doRenderTop = function () {
4221
4149
  var stage = topStageRef.current;
4222
4150
  var layer = topLayerRef.current;
4223
- if (!stage || !layer || topStageZIndex === undefined || !topOnHover) return;
4151
+ if (!stage || !layer || topStageZIndex === undefined) return;
4224
4152
  var hovered = hoveredItemRef.current;
4225
4153
  var shape = layer.findOne('.top-render-shape'); // hover된 항목이 없으면 shape 제거
4226
4154
 
@@ -4248,6 +4176,8 @@ var CanvasMarkerLayer = function (props) {
4248
4176
 
4249
4177
 
4250
4178
  shape.sceneFunc(function (konvaContext) {
4179
+ var _a;
4180
+
4251
4181
  var ctx = konvaContext;
4252
4182
  var currentHovered = hoveredItemRef.current; // hover된 항목이 없으면 아무것도 그리지 않음
4253
4183
 
@@ -4257,10 +4187,11 @@ var CanvasMarkerLayer = function (props) {
4257
4187
  return;
4258
4188
  }
4259
4189
 
4260
- var selectedItems = mapValuesToArray(selectedItemsMapRef.current);
4190
+ var selectedItems = mapValuesToArray(selectedItemsMapRef.current); // selectedItem이 있으면 hover된 항목이 선택되었는지 확인
4191
+
4261
4192
  var hoveredIsSelected = selectedItems.some(function (item) {
4262
4193
  return item.id === currentHovered.id;
4263
- }); // Top Layer에서는 hover된 마커만 hover 스타일로 그리기
4194
+ }) || ((_a = selectedItemRef.current) === null || _a === void 0 ? void 0 : _a.id) === currentHovered.id; // Top Layer에서는 hover된 마커만 hover 스타일로 그리기
4264
4195
  // renderEvent가 있으면: base는 그리지 않고 event만 그리기 (hover 스타일 적용)
4265
4196
  // renderEvent가 없으면: base를 hover 스타일로 그리기
4266
4197
 
@@ -4269,10 +4200,10 @@ var CanvasMarkerLayer = function (props) {
4269
4200
  var hoverSelectedItems = hoveredIsSelected ? [currentHovered] : [];
4270
4201
  renderEvent({
4271
4202
  ctx: ctx,
4203
+ hasTopStage: true,
4272
4204
  hoveredItem: currentHovered,
4273
4205
  selectedItem: selectedItemRef.current,
4274
4206
  selectedItems: hoverSelectedItems,
4275
- topOnHover: topOnHover,
4276
4207
  utils: renderUtils
4277
4208
  });
4278
4209
  } else {
@@ -4303,13 +4234,13 @@ var CanvasMarkerLayer = function (props) {
4303
4234
  topContainerRef.current.style.transform = containerRef.current.style.transform || '';
4304
4235
  }
4305
4236
 
4306
- if (topStageZIndex !== undefined && topOnHover) {
4237
+ if (topStageZIndex !== undefined) {
4307
4238
  doRenderTop();
4308
4239
  }
4309
4240
  }; // 지도 이벤트 핸들러 생성
4310
4241
 
4311
4242
 
4312
- var _h = createMapEventHandlers({
4243
+ var _f = createMapEventHandlers({
4313
4244
  accumTranslateRef: accumTranslateRef,
4314
4245
  boundingBoxCacheRef: boundingBoxCacheRef,
4315
4246
  containerRef: containerRef,
@@ -4320,12 +4251,30 @@ var CanvasMarkerLayer = function (props) {
4320
4251
  prevCenterOffsetRef: prevCenterOffsetRef,
4321
4252
  renderAllImmediate: renderAllImmediate
4322
4253
  }),
4323
- handleIdle = _h.handleIdle,
4324
- handleZoomStart = _h.handleZoomStart,
4325
- handleZoomEnd = _h.handleZoomEnd,
4326
- handleCenterChanged = _h.handleCenterChanged,
4327
- handleDragStartShared = _h.handleDragStart,
4328
- handleDragEndShared = _h.handleDragEnd;
4254
+ handleIdleShared = _f.handleIdle,
4255
+ handleZoomStart = _f.handleZoomStart,
4256
+ handleZoomEnd = _f.handleZoomEnd,
4257
+ handleCenterChangedShared = _f.handleCenterChanged,
4258
+ handleDragStartShared = _f.handleDragStart,
4259
+ handleDragEndShared = _f.handleDragEnd; // handleIdle 래핑: topStage transform 제거 추가
4260
+
4261
+
4262
+ var handleIdle = function () {
4263
+ handleIdleShared(); // 드래그 완료 시 topStage의 transform도 제거 (메인 stage와 동기화)
4264
+
4265
+ if (topStageZIndex !== undefined && topContainerRef.current) {
4266
+ topContainerRef.current.style.transform = '';
4267
+ }
4268
+ }; // handleCenterChanged 래핑: topStage transform 동기화 추가
4269
+
4270
+
4271
+ var handleCenterChanged = function () {
4272
+ handleCenterChangedShared(); // 드래그 중 메인 stage의 transform을 topStage에도 동기화 (반대 방향 이동 방지)
4273
+
4274
+ if (topStageZIndex !== undefined && topContainerRef.current && containerRef.current) {
4275
+ topContainerRef.current.style.transform = containerRef.current.style.transform || '';
4276
+ }
4277
+ };
4329
4278
 
4330
4279
  var handleDragStart = function () {
4331
4280
  handleDragStartShared(); // 드래그 시작 시점의 hover 상태 저장
@@ -4353,8 +4302,8 @@ var CanvasMarkerLayer = function (props) {
4353
4302
 
4354
4303
 
4355
4304
  var findData = function (offset) {
4356
- // topOnHover 옵션이 켜져 있으면 hover된 항목을 최우선으로 확인
4357
- if (topOnHover && hoveredItemRef.current) {
4305
+ // topStageZIndex가 설정되어 있으면 hover된 항목을 최우선으로 확인
4306
+ if (topStageZIndex !== undefined && hoveredItemRef.current) {
4358
4307
  var hovered = hoveredItemRef.current;
4359
4308
 
4360
4309
  if (isPointInMarkerData(offset, hovered, getOrComputeMarkerOffset)) {
@@ -4391,57 +4340,40 @@ var CanvasMarkerLayer = function (props) {
4391
4340
  controller.setMapCursor(hoveredData ? 'pointer' : 'grab');
4392
4341
  }
4393
4342
 
4394
- if (topStageZIndex !== undefined && topOnHover) {
4395
- // topStageZIndex가 설정되고 topOnHover가 true인 경우 Top Layer에서 hover된 항목 렌더링
4396
- // base 레이어와 event 레이어도 업데이트 (hover 항목 제외)
4397
- doRenderBase();
4343
+ if (topStageZIndex !== undefined) {
4344
+ // topStageZIndex가 설정된 경우 Top Layer에서 hover된 항목 렌더링
4345
+ // Base Layer는 모든 마커를 포함하므로 hover 상태 변경 시 재렌더링 불필요
4346
+ // Event Layer는 hover 스타일과 선택된 항목을 렌더링하므로 업데이트 필요
4398
4347
  doRenderEvent();
4399
4348
  doRenderTop();
4400
4349
  } else if (renderEvent) {
4401
- // renderEvent가 있을 때는 Event Layer 업데이트
4402
- // topOnHoverfalse일 때는 Base Layer에서도 hover 스타일을 적용해야 하므로 Base Layer도 업데이트
4403
- if (!topOnHover) {
4404
- doRenderBase();
4405
- }
4406
-
4350
+ // renderEvent가 있을 때는 Event Layer 업데이트
4351
+ // topStageZIndex없으면 Base Layer 정적이므로 재렌더링 불필요 (성능 우선)
4352
+ // hover 효과는 Event Layer에서만 처리하면 됨
4407
4353
  doRenderEvent();
4408
- } else if (topOnHover) {
4409
- doRenderBase();
4410
4354
  }
4411
- }; // 클릭 처리: 선택 상태 업데이트
4355
+ }; // 클릭 처리: 선택 상태 업데이트 (단일 선택만 지원)
4412
4356
 
4413
4357
 
4414
4358
  var handleLocalClick = function (clickedData) {
4415
- if (enableMultiSelect) {
4416
- var newSelected = new Set(selectedIdsRef.current);
4359
+ var newSelected = new Set();
4417
4360
 
4418
- if (newSelected.has(clickedData.id)) {
4419
- newSelected.delete(clickedData.id);
4420
- selectedItemsMapRef.current.delete(clickedData.id);
4421
- } else {
4422
- newSelected.add(clickedData.id);
4423
- selectedItemsMapRef.current.set(clickedData.id, clickedData);
4424
- }
4361
+ if (!selectedIdsRef.current.has(clickedData.id)) {
4362
+ newSelected.add(clickedData.id);
4363
+ selectedItemsMapRef.current.clear();
4364
+ selectedItemsMapRef.current.set(clickedData.id, clickedData); // externalSelectedItem이 있을 때를 대비해 selectedItemRef도 업데이트
4425
4365
 
4426
- selectedIdsRef.current = newSelected;
4366
+ selectedItemRef.current = clickedData;
4427
4367
  } else {
4428
- var newSelected = new Set();
4429
-
4430
- if (!selectedIdsRef.current.has(clickedData.id)) {
4431
- newSelected.add(clickedData.id);
4432
- selectedItemsMapRef.current.clear();
4433
- selectedItemsMapRef.current.set(clickedData.id, clickedData);
4434
- } else {
4435
- selectedItemsMapRef.current.clear();
4436
- }
4437
-
4438
- selectedIdsRef.current = newSelected;
4368
+ selectedItemsMapRef.current.clear();
4369
+ selectedItemRef.current = null;
4439
4370
  }
4440
4371
 
4441
- doRenderBase();
4372
+ selectedIdsRef.current = newSelected; // 선택 상태 변경은 Event Layer에서만 처리 (Base Layer는 정적이므로 재렌더링 불필요)
4373
+
4442
4374
  doRenderEvent();
4443
4375
 
4444
- if (topStageZIndex !== undefined && topOnHover) {
4376
+ if (topStageZIndex !== undefined) {
4445
4377
  doRenderTop();
4446
4378
  }
4447
4379
  }; // 클릭 이벤트 핸들러
@@ -4505,18 +4437,15 @@ var CanvasMarkerLayer = function (props) {
4505
4437
  hoveredItemRef.current = null;
4506
4438
  controller.setMapCursor('grab');
4507
4439
 
4508
- if (topStageZIndex !== undefined && topOnHover) {
4509
- // base 레이어와 event 레이어도 업데이트 (hover 항목 다시 표시)
4510
- doRenderBase();
4440
+ if (topStageZIndex !== undefined) {
4441
+ // Base Layer는 모든 마커를 포함하므로 hover 상태 변경 시 재렌더링 불필요
4442
+ // Event Layer는 hover 스타일과 선택된 항목을 렌더링하므로 업데이트 필요
4511
4443
  doRenderEvent();
4512
4444
  doRenderTop();
4513
4445
  } else if (renderEvent) {
4514
- // renderEvent가 있을 때는 Event Layer 업데이트
4515
- // topOnHoverfalse일 때는 Base Layer에서도 hover 스타일을 제거해야 하므로 Base Layer도 업데이트
4516
- if (!topOnHover) {
4517
- doRenderBase();
4518
- }
4519
-
4446
+ // renderEvent가 있을 때는 Event Layer 업데이트
4447
+ // topStageZIndex없으면 Base Layer 정적이므로 재렌더링 불필요 (성능 우선)
4448
+ // hover 효과 제거는 Event Layer에서만 처리하면 됨
4520
4449
  doRenderEvent();
4521
4450
  }
4522
4451
 
@@ -4525,9 +4454,9 @@ var CanvasMarkerLayer = function (props) {
4525
4454
 
4526
4455
 
4527
4456
  useEffect(function () {
4528
- divElement.style.width = 'fit-content'; // Top Layer용 div도 초기화 (topStageZIndex가 설정되고 topOnHover가 true인 경우)
4457
+ divElement.style.width = 'fit-content'; // Top Layer용 div도 초기화 (topStageZIndex가 설정된 경우)
4529
4458
 
4530
- if (topStageZIndex !== undefined && topOnHover) {
4459
+ if (topStageZIndex !== undefined) {
4531
4460
  topDivElement.style.width = 'fit-content';
4532
4461
  }
4533
4462
 
@@ -4713,10 +4642,10 @@ var CanvasMarkerLayer = function (props) {
4713
4642
 
4714
4643
  renderAllImmediate();
4715
4644
  }
4716
- }, [enableViewportCulling]); // Top Layer용 별도 캔버스 DOM 생성 (topStageZIndex가 설정되고 topOnHover가 true인 경우)
4645
+ }, [enableViewportCulling]); // Top Layer용 별도 캔버스 DOM 생성 (topStageZIndex가 설정된 경우)
4717
4646
 
4718
4647
  useEffect(function () {
4719
- if (topStageZIndex === undefined || !topOnHover) return;
4648
+ if (topStageZIndex === undefined) return;
4720
4649
  if (!topContainerRef.current) return;
4721
4650
  var mapDiv = controller.mapDivElement; // Top Layer용 div 요소 설정
4722
4651
 
@@ -4785,13 +4714,14 @@ var CanvasMarkerLayer = function (props) {
4785
4714
 
4786
4715
 
4787
4716
  var handleTopIdle = function () {
4788
- // topMarker의 position을 메인 marker와 동일하게 업데이트
4717
+ // 드래그 완료 후 topMarker의 position을 메인 marker와 동일하게 업데이트
4789
4718
  updateTopMarkerPosition(); // topStage 크기 업데이트
4790
4719
 
4791
4720
  if (topStageRef.current) {
4792
4721
  topStageRef.current.width(mapDiv.offsetWidth);
4793
4722
  topStageRef.current.height(mapDiv.offsetHeight);
4794
- } // 메인 stage의 transform topStage에도 동기화
4723
+ } // 드래그 완료 transform handleIdle에서 제거되므로 여기서는 동기화만
4724
+ // (handleIdle이 먼저 실행되어 transform을 제거한 후, 여기서 position 업데이트)
4795
4725
 
4796
4726
 
4797
4727
  if (topContainerRef.current && containerRef.current) {
@@ -4820,13 +4750,18 @@ var CanvasMarkerLayer = function (props) {
4820
4750
  };
4821
4751
 
4822
4752
  var handleTopCenterChanged = function () {
4823
- // topMarker의 position 메인 marker와 동일하게 업데이트
4824
- updateTopMarkerPosition(); // topStage 크기 업데이트
4753
+ // 드래그 중에는 transform만 동기화 (position 업데이트는 드래그 완료 후에만)
4754
+ // 드래그 중에 position을 업데이트하면 transform과 충돌하여 반대 방향으로 이동하는 버그 발생
4755
+ if (!draggingRef.current) {
4756
+ // 드래그가 아닐 때만 topMarker의 position을 업데이트
4757
+ updateTopMarkerPosition();
4758
+ } // topStage 크기 업데이트
4759
+
4825
4760
 
4826
4761
  if (topStageRef.current) {
4827
4762
  topStageRef.current.width(mapDiv.offsetWidth);
4828
4763
  topStageRef.current.height(mapDiv.offsetHeight);
4829
- } // 메인 stage의 transform을 topStage에도 동기화
4764
+ } // 메인 stage의 transform을 topStage에도 동기화 (드래그 중 필수)
4830
4765
 
4831
4766
 
4832
4767
  if (topContainerRef.current && containerRef.current) {
@@ -4868,25 +4803,39 @@ var CanvasMarkerLayer = function (props) {
4868
4803
  }, [topStageZIndex, renderEvent, options]); // 외부 selectedItems 동기화
4869
4804
 
4870
4805
  useEffect(function () {
4871
- if (!stageRef.current) return;
4872
- syncExternalSelectedItems(externalSelectedItems, selectedIdsRef, selectedItemsMapRef);
4873
- doRenderBase();
4806
+ if (!stageRef.current) return; // externalSelectedItems가 있으면 selectedItem은 무시 (공존 불가)
4807
+
4808
+ if (externalSelectedItems !== undefined) {
4809
+ selectedItemRef.current = undefined;
4810
+ syncExternalSelectedItems(externalSelectedItems, selectedIdsRef, selectedItemsMapRef);
4811
+ } // 선택 상태 변경은 Event Layer에서만 처리 (Base Layer는 정적이므로 재렌더링 불필요)
4812
+
4813
+
4874
4814
  doRenderEvent();
4875
4815
 
4876
- if (topStageZIndex !== undefined && topOnHover) {
4816
+ if (topStageZIndex !== undefined) {
4877
4817
  doRenderTop();
4878
4818
  }
4879
4819
  }, [externalSelectedItems]); // 외부 selectedItem 변경 시 Event Layer 리렌더링
4880
4820
 
4881
4821
  useEffect(function () {
4882
- if (!stageRef.current) return;
4883
- selectedItemRef.current = externalSelectedItem;
4822
+ if (!stageRef.current) return; // externalSelectedItem이 있으면 selectedItems는 무시 (공존 불가)
4823
+
4824
+ if (externalSelectedItem !== undefined) {
4825
+ selectedIdsRef.current.clear();
4826
+ selectedItemsMapRef.current.clear();
4827
+ selectedItemRef.current = externalSelectedItem;
4828
+ } else if (externalSelectedItems === undefined) {
4829
+ // 둘 다 없으면 selectedItemRef만 업데이트 (내부 클릭으로 선택한 항목은 유지)
4830
+ selectedItemRef.current = externalSelectedItem;
4831
+ }
4832
+
4884
4833
  doRenderEvent();
4885
4834
 
4886
- if (topStageZIndex !== undefined && topOnHover) {
4835
+ if (topStageZIndex !== undefined) {
4887
4836
  doRenderTop();
4888
4837
  }
4889
- }, [externalSelectedItem]); // 데이터 변경 시 렌더링 (캐시 정리 및 선택 상태 동기화)
4838
+ }, [externalSelectedItem, externalSelectedItems]); // 데이터 변경 시 렌더링 (캐시 정리 및 선택 상태 동기화)
4890
4839
 
4891
4840
  useEffect(function () {
4892
4841
  if (!stageRef.current) return;