draggable

ドラッグ可能オブジェクトは、ワークスペースに存在するレンダリングされたオブジェクトで、ドラッグ&ドロップできます。IDraggable インターフェースを実装します。

新しいレンダリングされたオブジェクトを Blockly に追加できないため、新しいドラッグ可能オブジェクト(マルチ選択プラグインや、既存のオブジェクトによるドラッグ処理方法の変更など)を追加する状況はほとんどありません。ワークスペース内に存在できるレンダリングされたオブジェクトは、ブロック、バブル、ワークスペースのコメントのみです。

責任

ドラッグ操作の実行時、Draggable にはいくつかの役割があります。

実装

新しいドラッグ可能物を作成するには、IRenderedElement インターフェースと IDraggable インターフェースを実装する必要があります。これにより、オブジェクトが表示可能で、ドラッグ可能であることを Blockly に通知できます。

class MyDraggable extends IRenderedElement, IDraggable {}

ルート SVG 要素を返す

getRootSvg メソッドは、ドラッグ可能なビューを構成する他のすべての要素を含むルート svg 要素(通常はグループ)を返します。

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

選択されるようにするには、Draggable に 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 インターフェースを実装して、Draggable をコピーできるようにし、IPaster を定義して貼り付けられるようにできます。

コピーと貼り付けについて詳しくは、コピーと貼り付けをご覧ください。