6
1

More than 1 year has passed since last update.

スベルトさん。第1話:Svelteのコンポーネントに属するファンクションを外部からコールする。(読み物 / 連載予定)

Last updated at Posted at 2022-06-18

はじめに

これはフィクションです。

read.pngチームリーダー
51くん、Svelte確かやってたよね?! この会社、他の人はReactかVueしかやってないないからちょっとお願いしたいことが有るんだけれど。

man.png51
まぁ、しょうがないですね。Svelteはマイナーですし、求人は殆どReactかVueですからね。で、お願いは何ですか?

read.pngチームリーダー
ちょっと変わったクライアントさんがいてSvelteで開発をしたいそうなんだよ。それで新人の、まりも君にちょっとSvelteの基礎を教えてくれないかな? まずは良くあるTo doリストから初めてくれると助かるよ。

man.png51
勿論良いですよ。

read.pngチームリーダー
ひとつ条件が有るんだけれど、To do リストのコンポーネントはロジックと入力のUIを持っていて、登録と削除のUIは外部に出したいんだ、To doコンポーネントには手を入れず、デザイナーが実装時にデザイン自由に変えたいらしいので。

man.png51
わかりました、つまりこうゆうことですね。

今回作るコンポーネント(To do コンポーネント):

  • To doの保持
  • To doのインプットのUI
  • 登録と削除機能(外部からのコール可)

外部コンポーネント(サンプル): ←デザイナーが触るのはこちらだけにしたい。

  • To doコンポーネント配置
  • 登録、削除のUIとその機能の呼び出し

read.pngチームリーダー
そうそう、多分、そんな感じ。じゃあ、後よろしく~。

いよいよ実装

asian.pngまりも
51さん、よろしくお願いいたします。

man.png51
こちらこそ。ではまずTo doコンポーネントの実装をお願いします。To doはtodoという配列に保持して、登録と削除はそれぞれpushとpopというファンクションに実装してください。

asian.pngまりも
できました。

man.png51
おー、早いね。どれどれ。さずが、まりも君! 良い感じに出来てるね。一つだけ。
今回の本題からは外れるけど、この配列を更新するときにpush, popを使うと値が更新されていることにならないのでUIが更新されないんだよ。

Todo.svelte
function push() {
+  todo = [value, ...todo];
-  todo.push(value);
}

man.png51
こんな風に書き換えると、値が更新されたことになるんだ。

asian.pngまりも
なるほどですね。

さて本題

man.png51
他は良い感じにできているので、本題に移ろう。
先ずはto doコンポーネントのファンクションを外部から参照できるようにしてみよう。

asian.pngまりも
いよいよですね。ドキドキします。

man.png51
ドキドキさせて申し訳ないくらい簡単なんだよ。exportを参照させたいファンクションの前に追加する。それだけ。

Todo.svelte
function push() {
	let todo = [];
	let value;
	
+       export function push() {  // exportを追加!
-       function push() {
		if(value && value.trim().length > 0)
			todo = [value, ...todo];
		value = '';
	}
+       export function pop() {  // exportを追加!
-       function pop() {
		todo.pop();
		todo = [...todo];
	}
}

asian.pngまりも
えっ、それだけですか?!もうRxxtとかやってられなくなりますね。

man.png51
では次に、これらファンクションをコールする側を実装してみよう。これも簡単だよ。
先ずは、to doコンポーネントのthisをバインドして、呼び出し側の変数と紐づける。

App.svelte
<script>
  import Todo from './Todo.svelte';
  let todo;
</script>
<Todo bind:this={todo}/>  //thisをバインドして変数todoと紐づけ

man.png51
後は、まりも君が想像している通りthis.ファンクション名という形でファンクションを呼び出すだけだよ。
今回はボタンのクリックで呼び出すように実装してみたよ。

App.svelte
<script>
  import Todo from './Todo.svelte';
  let todo;
</script>
<Todo bind:this={todo}/>  //thisをバインドして変数todoと紐づけ
+ <button on:click={todo.push}>Push</button>  //ボタンのクリックイベントでpushファンクションをコール

asian.pngまりも
簡潔だし、thisをバインドしてそのファンクションを呼び出すっていうのは理にかなっているというか直感的に理解できますね。それに比べるとRxxtとかは....。

まとめ

man.png51
じゃあ今回学んだことを整理してみよう。

ファンクションが呼ばれる側でやること:

  • 呼ばれるファンクションにexportを付加する。

呼ぶ側でやること:

  • 呼びたいコンポーネントのthisをバインドして、自分の変数と紐づけ。
  • this+ファンクション名でファンクションをコール

asian.pngまりも
とても良くわかりました。すっかりSvelteのファンになりそうです。

man.png51
じゃあ、まりも君。最後にコード全体を張っておいてくれるかな? あとReplのリンクもよろしくね。

asian.pngまりも
わかりました!!下に貼っておきます。
見づらいのでスタイルは削除しておきました。Replの方には残っています。

ToDo.svelte
<!-- script-->
<script>
	let todo = [];
	let value;
	
	export function push() {
		if(value && value.trim().length > 0)
			todo = [value, ...todo];
		value = '';
	}
	export function pop() {
		todo.pop();
		todo = [...todo];
	}
</script>


<!-- html-->
<input type='text' bind:value={value}>
<ul>
	{#each todo as item}
		<li>{item}</li>
	{/each}
</ul>

App.svelte
<script>
	import Todo from './Todo.svelte';
	//This gonna be binded to Todo instance
	let todo;

	function onKeyDown(event) {
		// Call Todo instance methods
		event.key === 'Enter' && todo.push();
	}
</script>


<!-- Bind Todo itself and call its' method -->
<div>
	<Todo bind:this={todo}/>
</div>
<!-- buttons calling Todo's method -->
<div>
	<button on:click={todo.push} id='push'>Push</button>	<!-- Call Todo's push method -->
	<button on:click={todo.pop} id='pop'>Pop</button>	<!-- Call Todo's pop method -->
</div>

<svelte:window on:keydown={onKeyDown} />

Replのリンクはこちら。Call function inside of a component from the component

asian.pngまりも
51さん。今回は親が子のファンクションを呼ぶ形でしたが、逆はどうやるんでしょうか?子が親のファンクションを呼びたい時は?

man.png51
流石、まりも君、好奇心旺盛だね。それはまた次の機会まで待っててね。

次回予告

112_sazae.jpg
まりもです。先日仮想通貨の下落に伴ってグラボが値下がりしていると聞きました。これを機会に数十枚大人買いしようかと画策している最中です。でも夏は暑そうですね。うちは冷房が無いので冷えピタで毎年しのいでいます。冷えピタはグラボにも有効でしょうか?
さーて次回のスベルトさんは!

  • 子供、親なしじゃ生きられない。親、子なしじゃ生きられない
  • 親は子供を選べるが、子供は親を選べない
  • 子供、孫、ひ孫までじいちゃんを呼び出す

の三本です!

これはフィクションです。

Markdownの使い方が本来意図された使い方と異なるなどの批判は受け付けません。

6
1
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
6
1