4
3

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 3 years have passed since last update.

Angular Materialでドラッグ&ドロップを実装する(cdk/drag-drop)

Last updated at Posted at 2021-07-27

#目次
1.はじめに
2.フレームワークとライブラリ
3.サンプルコード
4.サンプルコードの表示
5.htmlの疑似コード
6.tsの疑似コード
7.dropメソッド
8.付録
9.注意点
10.参考資料
11.最後に一言

#1. はじめに

田中です。近年、WebブラウザのSPA(シングルページアプリケーション)のプラットフォームにて、ドラッグ&ドロップ機能のライブラリが公式で提供されるようになり、直感的なUIを使えるWebページが、とても作りやすい時代になりました。

そこで今回は、ドラッグ&ドロップ機能を実現するライブラリのサンプルコードについて、htmlとtsを疑似コード(プログラムの一部を日本語にしたもの)に翻訳してみようと思います。

ゴールは、このような書き方で使えます。ということだけを知ってもらうところですので、気楽に読んでみてください。

※深くは解説していませんのであしからず。m(_ _)m

※免責事項(必ず、ご一読ください)
  本記事の情報により生じた、いかなる損害や損失についても、当社は一切の責任を負いかねます。
  また、誤情報が入り込んだり、情報が古くなったりすることもありますので、必ずしも正確性を保証するものではありませんのでご了承ください。

#2. フレームワークとライブラリ
今回はAngular Materialcdk/drag-dropを使用します。
 Drag and Drop(@angular/cdk/drag-drop)

#3. サンプルコード
上記公式サイトのサンプルコードTransferring items between listsを使用します。
To Doのリストのアイテムをマウスで左クリックしたまま、Doneのリストに移す動作を実現させます。
image.png

#4. サンプルコードの表示
<>をクリックすることで、HTML、TS、CSSが表示されます。
image.png

#5. htmlの疑似コード

HTMLのソースコードの大事なところに絞って解読すると下記のようになります。

htmlファイルの疑似コード

<div class="コンテナーに適用するcssのスタイル">
<h2>リスト1のタイトル<h2>

 <div
  cdkDropList
  #リスト1="cdkDropList"
  [cdkDropListData]="リスト1に適用するts内の配列"
  [cdkDropListConnectedTo]="[リスト2]"
  class="リスト1に適用するcssのスタイル"
  (cdkDropListDropped)="ドロップ時に動くメソッド"
  <div class="アイテムに適用するcssのクラス" *ngFor="let リスト1のアイテム of リスト1に適用するts内の配列" cdkDrag>{{リスト1のアイテム}}</div>
 </div>
</div>

<div class="コンテナーに適用するcssのスタイル">
<h2>リスト2のタイトル</h2>

  <div
   cdkDropList
   #リスト2="cdkDropList"
   [cdkDropListData]="リスト2に適用するts内の配列"
    [cdkDropListConnectedTo]="[リスト1]"
   class="リスト2に適用するcssのスタイル"
   (cdkDropListDropped)="ドロップ時に動くメソッド"
   <div class="アイテムに適用するcssのクラス"  *ngFor="let リスト2のアイテム of リスト2に適用するts内の配列"cdkDrag>{{リスト2のアイテム}}</div>
  </div>
</div>

#6. tsの疑似コード

tsのソースコードも同様に解読してみます。

tsファイルの概形
import {Component} from '@angular/core';
import {CdkDragDrop, moveItemInArray, transferArrayItem} from '@angular/cdk/drag-drop';
@Component({
  selector: 'cdk-drag-drop-connected-sorting-example',
  templateUrl: 'cdk-drag-drop-connected-sorting-example.html',
  styleUrls: ['cdk-drag-drop-connected-sorting-example.css'],
})
export class CdkDragDropConnectedSortingExample {
  リスト1の配列 = [
  ~リスト1のアイテムを定義~
  ];
  リスト2の配列 = [
  ~リスト2アイテムを定義~
  ];
  drop(イベント: CdkDragDrop<string[]>) {
  ~dropイベント発生時の処理内容~
 }
}

#7. dropメソッド
dropメソッドも解読してみます。eventを使って、dropメソッド内部に閉じた形で書くことができます。

dropメソッド
  drop(イベント: CdkDragDrop<string[]>) {
    if (移動前のリスト === 移動先のリスト) {
      moveItemInArray(移動先のリスト, 移動前のリスト,移動先のリストにおけるアイテムの内部的な番号);
    } else {
      transferArrayItem(移動前のリスト,
                        移動先のリスト,
                        移動前のリストにおけるアイテムの内部的な番号,
                        移動先のリストにおけるアイテムの内部的な番号);
    }
  }

#8. 付録
上記のサンプルコードを改造して、CdkDragDropのリストの中にCdkDragDropのリストといった、多重構造のドラッグ&ドロップ可能なリストを作ってみました。
image.png
なお、試して分かったことなのですが、子のリストのアイテムを別の親のリストにドロップすることはできませんでした。
そのようなことをする場合、同様なJSフレームワークの「Vue」の「Vue.Draggable」ライブラリを使うとよいようなので、こちらも後学のため、勉強してみたいと思います。

 著者:rito様
 URL:Vue.jsでドラッグアンドドロップによる要素の並べ替えと移動を実装する

#9. 注意点
・リストの中のアイテムを構造体で定義する場合、プロパティ名は**"id"以外を使用してください。
 listのプロパティに
id: numberを使用した場合
   ドラッグ&ドロップ後に、idが自動で昇順に置き換わり、意図しない動作となります。
 listのプロパティに
identity: number**を使用した場合
   こうすることで、ドラッグ&ドロップ後も、アイテムからみた固有識別番号が変化しません。

構造体定義例
export interface Hero {
  identity: number;
  name: string;
}

#10. 参考資料

#11. 最後に一言
 最後まで読んでいただき、ありがとうございます! 今後も新しいWeb技術を取り込んでいこうと思います。

4
3
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
4
3

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?