はじめに
Salesforceの新しいフロントエンドフレームワークであるLightning Web Componentのお話です。
lightning-datatable
コンポーネントはいわゆるSalesforceの一般的なテーブルUIを実現するコンポーネントです。
しかし、リンクが貼れない、ボタンが置けない、などなかなかカスタマイズが効きません。
追記(2019/04/08)
ボタンはtype:'button'
やtype:'button-icon'
で置けました。
ちゃんとドキュメントを読んでみると、Create Custom Data Types
という章があることに気づいたので、試してみました。
しかし、ちょっとつまずいたので、記事にまとめて、コードも公開しておきます。
作るもの
ドキュメントの例のようにカラムにdeleteRowButton
というデータ型を指定すると削除ボタンを表示するようにします。
ソースコード
リポジトリ作って置いておきました。
https://github.com/atskimura/lightning-datatable-custom-datatype-example
作り方
3つのコンポーネントを作る必要があります。
- myDatatableDemo: 実際画面に配置するコンポーネント
- myDatatable: lightning-datatableを継承したコンポーネント
- datatableDeleteRowBtn: 削除ボタン部分のコンポーネント
myDatatableDemo
実際に画面に配置するコンポーネントです。カスタムdatatableコンポーネントを利用する側です。
<template>
<c-my-datatable
key-field="id"
data={data}
columns={columns}
ondeleterow={deleteRow}
hide-checkbox-column>
</c-my-datatable>
</template>
ビューではこの後作るmyDatatable
コンポーネントを利用しています。
ドキュメントと違って他のコンポーネントを利用するにはネームスペース(今回はローカルなのでc
)が必要です。
ondeleterow
はこの後作成するdatatableDeleteRowBtn
で発火します。
import { LightningElement, track } from 'lwc';
const columns = [
{
label: 'Name',
fieldName: 'name',
},
{
label: 'Delete',
type: 'deleteRowButton',
fieldName: 'id',
fixedWidth: 70,
typeAttributes: {
attrA: { fieldName: 'attrA' },
attrB: { fieldName: 'attrB' },
},
},
];
export default class MyDatatableDemo extends LightningElement {
@track data = [
{
id: '1',
name: 'Name1',
attrA: 'A1',
attrB: 'B1',
},
{
id: '2',
name: 'Name2',
attrA: 'A2',
attrB: 'B2',
}
];
@track columns = columns;
deleteRow(event) {
const { rowId } = event.detail;
window.console.log(rowId, event);
// Remove the row
}
}
columns
でlightning-datatable
コンポーネントにはないdeleteRowButton
というタイプを指定しています。
myDatatable
lightning-datatableを継承したコンポーネントです。カスタムデータタイプを使用するには継承したコンポーネントを作る必要があります。面倒ですね。
import LightningDatatable from 'lightning/datatable';
import deleteRow from './deleteRow.html';
export default class MyDatatable extends LightningDatatable {
static customTypes = {
deleteRowButton: {
template: deleteRow,
// Provide template data here if needed
typeAttributes: ['attrA', 'attrB'],
}
//more custom types here
};
}
LightningDatatable
を継承したクラスを作り、customTypes
に追加したいカスタムデータ型を定義するだけです。
利用するテンプレート(template
)と値を渡したいプロパティ名(typeAttributes
)を設定します。
<template>
<c-datatable-delete-row-btn
data-navigation="enable"
row-id={value}
attr-a={typeAttributes.attrA}
attr-b={typeAttributes.attrB}>
</c-datatable-delete-row-btn>
</template>
テンプレートはdeleteRow.html
としてmyDatatable.js
と同階層に作ります。
datatableDeleteRowBtn
コンポーネントを呼び出しています。
value
ではcolumns
の定義でfieldName
に指定したプロパティ値が取得できます。
typeAttributes.attrA
のようにするとそのカラムのデータのattrA
プロパティの値が取得できます。
こういうファイル構造になります。
myDatatable.html
は空でよいです。
datatableDeleteRowBtn
deleteRowButton
型に対応する削除ボタン部分のコンポーネントです。
これは普通にコンポーネントを作ればよいです。
<template>
<div style="text-align: center;">
<lightning-button-icon
icon-name="utility:delete"
onclick={fireDeleteRow}>
</lightning-button-icon>
</div>
</template>
ビューでは削除ボタンを置いているだけです。
import { LightningElement, api } from 'lwc';
// Accessibility module
// import { baseNavigation } from 'lightning/datatableKeyboardMixins';
// For the render() method
// import template from './datatableDeleteRowBtn.html';
// export default class DatatableDeleteRowBtn extends baseNavigation(LightningElement) {
export default class DatatableDeleteRowBtn extends LightningElement {
@api rowId;
@api attrA;
@api attrB;
/* // Required for mixins
render() {
return template;
}*/
fireDeleteRow() {
const event = CustomEvent('deleterow', {
composed: true,
bubbles: true,
cancelable: true,
detail: {
rowId: this.rowId,
},
});
this.dispatchEvent(event);
}
}
datatableKeyboardMixins
を使うとテーブル内でキーボードナビゲーションが使えるようになるらしいんですが、これの使い方わかりませんでした。コメントアウトしている箇所のようにドキュメント通りに書くと、何も表示されなくなってしまいます。誰か使い方わかったら教えてください。
それ以外は普通にコンポーネント作るだけです。
終わりに
lightning-datatable
使えないなあと思っていましたが、意外と使えるかもしれません。
マウスオーバーしたらポップオーバーを表示するデータ型なんかを作りたいなと思います。
次のリリースでそんなデータ型が標準で追加されそうですが…