Discourseでモーダルウィンドウ(ポップアップ/ダイアログ)をレンダリングするためのDModal APIの使用

Discourse 3.1.0.beta6 には、全く新しい \u003cDModal\u003e コンポーネントベースの API が搭載されています。

:information_source: これは古いコントローラーベースの API に取って代わるものであり、非推奨となりました。既存の古い API を使用しているモーダルについては、移行ガイドをこちらで確認してください。

モーダルのレンダリング

モーダルは、handlebars テンプレートに \u003cDModal\u003e コンポーネントを含めることでレンダリングされます。適切なテンプレートがまだない場合は、Using Plugin Outlet Connectors from a Theme or Plugin を確認してください。

シンプルなモーダルは次のようなものになります。

\u003cDButton
  @translatedLabel="モーダルを表示"
  @action={{fn (mut this.modalIsVisible) true}}
/\u003e

{{#if this.modalIsVisible}}
  \u003cDModal @title="マイモーダル" @closeModal={{fn (mut this.modalIsVisible) false}}\u003e
    こんにちは世界、これはモーダル内のコンテンツです
  \u003c/DModal\u003e
{{/if}}

:information_source: mut ヘルパーは、hbs のみで値を設定するための方法としてここで使用されています。modalIsVisible は、他の標準的な Ember メソッドを使用して設定することもできます。

この例では、次のようなシンプルなモーダルが作成されます。

コンポーネントへのラップ

さらに複雑な処理を導入する前に、新しいモーダルを独自のコンポーネント定義でラップするのが最善です。\u003cDModal\u003e の部分を新しい \u003cMyModal /\u003e コンポーネント内に移動しましょう。

{{! components/my-modal.hbs }}
\u003cDModal @title="マイモーダル" @closeModal={{@closeModal}}\u003e
  Hello world, this is some content in a modal
\u003c/DModal\u003e

対応する .js コンポーネントファイルを追加することで、より複雑なロジックや状態を導入できるようになります。

新しいコンポーネントを使用するには、呼び出し元を更新してそれを参照するようにし、@closeModal 引数を渡すようにします。

\u003cDButton
  @translatedLabel="モーダルを表示"
  @action={{fn (mut this.modalIsVisible) true}}
/\u003e

{{#if this.modalIsVisible}}
  \u003cMyModal @closeModal={{fn (mut this.modalIsVisible) false}} /\u003e
{{/if}}

フッターの追加

多くのモーダルには何らかのコールトゥアクションがあります。Discourse では、これらは通常モーダルの下部に配置されます。これを可能にするために、DModal にはコンテンツをレンダリングできるいくつかの「名前付きブロック」があります。ここでは、2 つのボタン(1 つは標準の DModalCancel ボタン)をフッターに追加するように例を更新します。

\u003cDModal @title="マイモーダル" @closeModal={{@closeModal}}\u003e
  \u003c:body\u003e
    Hello world, this is some content in a modal
  \u003c/:body\u003e
  \u003c:footer\u003e
    \u003cDButton class="btn-primary" @translatedLabel="送信" /\u003e
    \u003cDModalCancel @close={{@closeModal}} /\u003e
  \u003c/:footer\u003e
\u003c/DModal\u003e

非 hbs コンテキストからのモーダルのレンダリング

理想的には、\u003cDModal\u003e インスタンスは、上記で示した宣言的な手法を使用して Ember handlebars テンプレート内からレンダリングされるべきです。これがユースケースにとって実現不可能である場合(例:Discourse のレガシーな「raw-hbs」または「widget」レンダリングシステムからモーダルをトリガーする必要がある場合)、modal サービスをインジェクトし、modal.show() を呼び出すことで実行できます。

前述のように、モーダルを独自のコンポーネントでラップしていることを確認してください。次に、コンポーネントクラスへの参照を showModal に渡すことで、モーダルをトリガーします。

import MyModal from "discourse/components/my-modal";

// (関連する場所に modal サービスをインジェクトします)

// モーダルを開きたいときはいつでもこの呼び出しを追加します。
// `@closeModal` 引数はコンポーネントに自動的に渡されます。
this.modal.show(MyModal);

// オプションで、「`model`」パラメーターを渡します。これはコンポーネントに `@model` として渡されます。
// これには、モーダルが使用するデータやアクション/コールバックを含めることができます。
this.modal.show(MyModal, {
  model: { topic: this.topic, someAction: this.someAction },
});

// `modal.show()` はプロミスを返すため、閉じられるのを待つことができます。
// これは、`@closeModal` アクションに渡されたデータで解決されます。
const result = await this.modal.show(MyModal);

さらなるカスタマイズ性!

\u003cDModal\u003e には多くの名前付きブロックと引数があります。引数についてはインタラクティブスタイルガイドを、名前付きブロックについてはd-modal テンプレート実装を確認してください。


\u003csmall\u003eこのドキュメントはバージョン管理されています - 変更提案はgithubでお願いします。\u003c/small\u003e

\u003c!-- START DOCS ASSET MAP
[
{
"local_path": "/assets/dmodal-api-1.png",
"local_sha1": "8dfd8ffa18409fdcac56e95e0f37e3b2c81af61e",
"remote_short_url": "upload://9eKVimqNmM9Q4apSPWsWrImfmQt.png"
},
{
"local_path": "/assets/dmodal-api-2.png",
"local_sha1": "9e6b3ae3a40c9934fa89cea18d42a1138e9248d3",
"remote_short_url": "upload://yp2hfxwO9dNjAJtUnGU89azmz63.png"
}
]
END DOCS ASSET MAP –\u003e

「いいね!」 17

投稿が新しいトピックに分割されました: head_tagからモーダルを表示できますか