Open1
Phoenix(LiveView)でAlpinejsを試してみたときの記録
これは2021年3月ごろのスクラップの整理です。
情報が古くなっているかもしれません。
導入
- Integrating Phoenix LiveView with JavaScript and AlpineJS
- Alpinejs Version2 と 3で設定に違いあり
--- a/assets/js/app.js
+++ b/assets/js/app.js
@@ -28,13 +28,15 @@ import topbar from "../vendor/topbar"
import Alpine from "alpinejs"
import Hooks from "./hooks"
+Alpine.start()
+
let csrfToken = document.querySelector("meta[name='csrf-token']").getAttribute("content")
let liveSocket = new LiveSocket("/live", Socket, {
params: { _csrf_token: csrfToken },
hooks: Hooks,
dom: {
- onBeforeElUpdated(from, to) {
- if (from.__x) { Alpine.clone(from.__x, to) }
+ onBeforeElUpdated(from, to){
+ if(from._x_dataStack){ Alpine.clone(from, to) }
}
}
})
どういうところで使うか
- サーバ側とのやり取りがない純粋なクライアント側でのUI操作
- テキストエリアのautoresize等はAlpine.jsに任せればよい典型
- How to make textarea auto-resize with Alpine.js
- リサイズした領域がLiveViewのその他描画でもどるなら
phx-update="ignore"
する
-
phx-click
後に別のアイテムにフォーカス(focus)したいときにphx-hook
やpush_event
ではできない(かった)が、x-on:click
をphx-click
と同じ要素に設定して行う(とできた) - 「作成」「続けて作成」といったサブミットボタンが2つあるようなフォームにおいて、押したボタンに沿って処理を行いたいときなど、
phx-submit="submit"
が送られる前にx-on:click=
でhiddenなアイテムに値をセットする
form phx-submit="submit" x-data="{context: null}"
input type="hidden" name="context" x-model="context"
div x-on:click="context = 'a'; $nextTick(() => $refs.submit.click())"
| submitA
div x-on:click="context = 'b'; $nextTick(() => $refs.submit.click())"
| submitB
button x-ref="submit"
LiveViewとのデータ更新の兼ね合い
- 基本的にLiveViewで更新も行うようなリソースでは、複雑になるので使わない方がいい
-
x-data="{}"
のなかで assignされた値を使っている場合、いずれかの値が変わったタイミングにおいて、再度初期化される - 例えば、テキストエリアをsubmitごとに初期化したいなら
form x-data="{ text: '', _timestamp: '<%= @timestamp %>' }"
のような小細工がいる - これはsubmit時に初期化するようなイベントを発行するか、changeset由来のformにできる(推奨かな?)のであれば、changesetでするのが適切
- Alpine.js側(
x-on:click
等)からHook側の処理を動かす場合は、独自イベントをHook側で作っておいて、それをdispatchする - Alpinejsの表現力、例えば
x-on:click.away
を生かす場合は、x-on:click
で別のphx-click
イベントが定義されたタグに対してclick()
イベントを送るなどもあり。- 例えば、モーダルで"表示領域以外をクリックされたときに閉じる"を実現する際に、イベント検知自体をAlpinejsを有効活用(.away)して、他のタグに設定されているphxなイベントを起こす等
- LiveComponentのidを付ける大枠のタグでは、
x-data=
しないこと -
x-on:click=""
等が定義されている箇所をサーバ側で出し入れ(<%= if ~ %>
)すると、非表示=>表示時に発火してくれないときがあるので、x-show=""
で制御する方がよさそう
その他
- x-data に渡す内容に改行\nが入っていてエラーになるなら javascript_escape すると良さそう
x-data: { content: '<%= javascript_escape(content) %>' }
-
phx-submit
はx-on:click=$el.submit()
では発火しない-
x-on:click=$refs.submit.click()
等でclick()
する
-