맞춤 드래그 가능

드래그 가능한 항목은 작업공간에 있으며 드래그 앤 드롭할 수 있는 렌더링된 객체입니다. IDraggable 인터페이스를 구현합니다.

Blockly에 새로운 드래그 가능 항목을 추가하는 경우는 매우 드뭅니다 (예: 다중 선택 플러그인 또는 기존 객체가 드래그를 처리하는 방식 변경). Blockly에 렌더링된 새 객체를 추가할 수 없기 때문입니다. 작업공간 내에 있을 수 있는 렌더링된 객체는 블록, 풍선, 작업공간 댓글뿐입니다.

책임

드래그를 실행할 때 드래그 가능 요소에는 다음과 같은 여러 책임이 있습니다.

구현

새 드래그 가능 항목을 만들려면 IRenderedElementIDraggable 인터페이스를 구현해야 합니다. 이렇게 하면 Blockly가 객체가 표시되고 드래그할 수 있음을 알게 됩니다.

class MyDraggable extends IRenderedElement, IDraggable {}

루트 SVG 요소를 반환합니다.

getRootSvg 메서드는 드래그 가능한 항목의 뷰를 구성하는 다른 모든 요소를 보유하는 루트 svg 요소 (일반적으로 group)를 반환합니다.

getSvgRoot() {
  return this.rootSvg;
}

이동성 반환

isMovable 메서드는 드래그 가능한 항목이 현재 이동 가능한지 여부를 반환합니다 (객체 드래그를 일시적으로 사용 중지할 수 있음). isMovablefalse를 반환하면 작업공간이 대신 드래그됩니다.

isMovable() {
  return true;
}

반환 위치

getRelativeToSurfaceXY 메서드는 작업 공간 좌표에서 드래그 가능한 항목의 상단 시작 모서리 위치를 지정하는 Coordinate를 반환합니다.

작업공간 좌표의 원점은 작업공간의 절대 왼쪽과 절대 상단에 있습니다. 또한 워크스페이스의 크기를 조정하거나 이동해도 변경되지 않습니다.

getRelativeToSurfaceXY() {
  return this.loc;
}

드래그 시작

startDrag 메서드는 드래그 가능한 항목에서 드래그를 초기화합니다. 이 메서드는 드래그 가능한 항목을 이동하지 않습니다. 하지만 드래그를 완료하는 데 필요한 데이터를 저장하거나 객체를 구성해야 합니다. 여기에는 revertDrag가 호출될 경우 드래그를 되돌리는 데 필요한 데이터가 포함됩니다.

또한 svg 요소가 작업공간의 드래그 레이어에 있도록 변경하여 다른 요소 위에 표시되도록 해야 합니다.

또한 누른 키를 확인하는 데 사용할 수 있는 이벤트를 가져옵니다. 이를 통해 예를 들어 시프트를 누른 상태에서 드래그하는 것을 일반 드래그와 다르게 처리할 수 있습니다.

startDrag(e) {
  // Save the original location so we can revert the drag.
  this.startLoc = this.getRelativeToSurfaceXY();

  // Disable resizing the workspace for performance.
  this.workspace.setResizesEnabled(false);

  // Put the element on the drag layer.
  this.workspace.getLayerManager()?.moveToDragLayer(this);

  // Fire a drag event...

  // etc...
}

드래그

drag 메서드는 실제로 드래그 가능한 객체를 이동합니다. newLoc는 작업 공간 좌표에 있으며, 눌린 키를 확인하는 데 사용할 수 있는 이벤트도 전달됩니다.

drag(newLoc, e) {
  this.moveTo(newLoc);
}

드래그 되돌리기

revertDrag 메서드는 드래그 시작 시의 위치로 드래그 가능 항목을 반환합니다. 예를 들어 드래그 가능한 항목이 이동을 방지하는 드래그 타겟에 드롭되는 경우에 발생합니다.

revertDrag() {
  // Move back to the position that was stored in `startDrag`.
  this.moveTo(this.startLoc);
}

드래그 종료

endDrag 메서드는 드래그를 정리하여 저장된 데이터나 객체를 해제하고 드래그 가능한 요소를 원래 레이어로 반환합니다.

revertDrag가 호출되면 endDrag는 항상 revertDrag 다음에 호출됩니다.

endDrag() {
  // Put the element back on its original layer (in this case BLOCK).
  this.workspace
    .getLayerManager()
    ?.moveOffDragLayer(this, Blockly.layers.BLOCK);

  // Allow the workspace to start resizing again.
  this.workspace.setResizesEnabled(true);
}

선택

드래그되는 요소는 드래그가 감지될 때 선택된 요소에 의해 결정됩니다.

ISelectable

드래그 가능 항목이 선택되려면 ISelectable 인터페이스를 구현해야 합니다.

class MyDraggable implements ISelectable {
  constructor(workspace) {
    this.id = Blockly.utils.idGenerator.genUid();
    this.workspace = workspace;
  }

  select() {
    // Visually indicate this draggable is selected.
  }

  unselect() {
    // Visually indicate this draggable is not selected.
  }
}

선택 설정

선택된 요소는 Blockly.common.setSelected()를 호출하여 설정할 수 있습니다. 일반적으로 사용자의 pointerdown 이벤트에 대한 응답으로 이 작업을 수행합니다.

  constructor() {
    this.initSvg();

    Blockly.browserEvents.conditionalBind(
      this.getSvgRoot(),
      'pointerdown',
      this,
      () => Blockly.common.setSelected(this));
  }

호환성

드래그 가능한 항목은 Blockly의 다른 시스템과 상호작용할 수 있도록 추가 인터페이스를 구현할 수 있습니다.

삭제 가능

IDeleteable 인터페이스를 구현하여 드래그 가능한 항목이 휴지통이나 기타 삭제 타겟에 의해 삭제되도록 할 수 있습니다.

class MyDraggable implements IDeletable {
  isDeletable() {
    return true;
  }

  dispose() {
    // Dispose of any references to data or SVG elements.
  }

  setDeleteStyle() {
    // Visually indicate that the draggable is about to be deleted.
  }
}

복사 가능

ICopyable 인터페이스를 구현하여 드래그 가능한 항목을 복사하고 IPaster를 정의하여 붙여넣을 수 있습니다.

복사 및 붙여넣기에 대한 자세한 내용은 복사 및 붙여넣기를 참고하세요.