戻る

クラスのデリゲート
デリゲート

クラスのデリゲート処理は、あるオブジェクトが直接行わない処理を、
別のオブジェクトのメソッドに委譲することです。
クラスに委託先となるオブジェクトを保持させます。
その委託先のオブジェクトのメソッドを呼び出しデリゲートイベントを実行させます。

[サンプル]
copy
let notifier = null;
let used = 0;
const b1 = document.getElementById("ok");
const b2 = document.getElementById("ng");
const b3 = document.getElementById("reset");
b1.addEventListener("click", () => 
{
	if(used == 1) return;
	used = 1;
	notifier.sendNotification(0);
});
b2.addEventListener("click", () => 
{
	if(used == 1) return;
	used = 1;
	notifier.sendNotification(1);
});
b3.addEventListener("click", () => 
{
	const generator = new judgeProblem();
	generator.prepareProblem();
	notifier = new Notifier(generator);
	const result = document.getElementById("result");
	result.innerText = "";
	used = 0;

});
class judgeProblem 
{
	#answer = 0;//[0]◯ [1]✕
	#num1 = 0;
	#num2 = 0;
	judge(answer) 
	{
		this.#judgeAnswer(answer);
	}
	#judgeAnswer(answer)
	{
		const obj = document.getElementById('lang');
		let tmp ="";
		if(this.#answer == answer)
		{
			tmp = obj.value == 0 ? "正解" : "CORRECT";
		}
		else
		{
			tmp = obj.value == 0 ? "不正解" : "NOT CORRECT";
		}
		const result = document.getElementById("result");
		result.innerText = tmp;
	}

	prepareProblem()
	{
		this.#num1 = this.#problemNum();
		this.#num2 = this.#problemNum();
		this.#prepareAnswer();
	}
	#problemNum()
	{
		const start = 1;
		const end = 9;
		return this.#randomNum(start, end);
	}
	#prepareAnswer()
	{
		const start = 0;
		const end = 1;
		this.#answer = this.#randomNum(start, end);
		let result = this.#num1 + this.#num2;
		if(this.#answer == 1)
		{
			result++;
		}
		const problem = document.getElementById("problem");
		problem.innerText = this.#num1 + "+" + this.#num2 + "=" + result;
	}
	#randomNum(start, end)
	{
		return Math.floor(Math.random() * (end - start + 1)) + start;
	}
}

class Notifier 
{
	constructor(messageGenerator) 
	{
		this.messageGenerator = messageGenerator;
	}
	
	sendNotification(answer) 
	{
		this.messageGenerator.judge(answer);
	}
}
デリゲートを使用したサンプルです。
RESETボタンを選択すると
たし算と計算結果が表示されます。
計算結果が正しいなら◯ボタンを選択してください。
間違いなら✕ボタンを選択してください。
結果が問題の右側に表示されます。

b3.addEventListener("click", () =>
RESETボタンを選択

const generator = new judgeProblem();
generator.prepareProblem();
たし算の左側の数字、右側の数字と計算結果を準備します。

this.#num1 = this.#problemNum();
左側の数字を取得します。

#problemNum()
乱数で1から9までの範囲を取得するため下記の関数を実行しています。

return this.#randomNum(start, end);
Math.floor(Math.random() * (end - start + 1)) + start;
指定の範囲の整数を取得します。
Math.random
0以上1未満の浮動小数点(小数点以下を含む数字)の疑似乱数を生成します。
(end - start + 1)
取得したい乱数の範囲を計算します。
今回の例では問題の数は1から9まで範囲なので
start:1(最小)
end:9(最大)
この範囲は(9 - 1 + 1) = 9となります。
Math.random() * (end - start + 1)
0以上1未満 * 9(範囲の計算結果)の範囲を返すことになるため、
乱数としての範囲は0から9未満までの範囲となります。
計算式の全体は下記の通りです。
Math.floor(Math.random() * (end - start + 1)) + start;
Math.random()が返す値が「0.958」と仮定します。
Math.random() * (end - start + 1) = 0.958 * (9 - 1 + 1) = 8.62
Math.floorは切り捨てなので「8」を返します。
「Math.floor(Math.random() * (end - start + 1))」 + start
8 + 1 = 9
問題の数字として取得した数字は「9」となります。

this.#num2 = this.#problemNum();
右側の数字も左側と同様の考え方となります。

this.#prepareAnswer();
const start = 0;
const end = 1;
this.#answer = this.#randomNum(start, end);
正解を決めるため乱数で値を取得します。
let result = this.#num1 + this.#num2;
答えを計算します。
if(this.#answer == 1)
不正解の場合は、計算結果を間違えにする必要があるため、答えに1を加算した結果にします。
const problem = document.getElementById("problem");
problem.innerText = this.#num1 + "+" + this.#num2 + "=" + result;
問題を表示します。

notifier = new Notifier(generator);
Notifierクラスに委託先のクラスをjudgeProblemとするため
インスタンス化したjudgeProblemクラスオブジェクトを引数に追加します。
this.messageGenerator = messageGenerator;
NotifierクラスのconstructorでjudgeProblemオブジェクトを保持させます。
この準備をすることで委託先のオブジェクトのメソッドを呼び出すことができるようになります。

const result = document.getElementById("result");
result.innerText = "";
結果を表示するエリアをクリアします。
used = 0;
問題に答えるボタンを一度選択した場合、再度、選択することができないようにするためのフラグです。
そのためボタンを選択できるようにクリア状態にしておきます。

RESETボタンを実行した結果から正解を選択します。
ボタンのイベントより
notifier.sendNotification(0 or 1);
を実行します。
NotifierクラスのsendNotification(answer)
NotifierクラスのsendNotificationメソッドに押したボタンの種類を引数として渡して実行します。
this.messageGenerator.judge(answer);
すでにjudgeProblemクラスオブジェクトを保持した状態になっているため
judgeProblemクラスのjudge(answer) メソッドを実行しています。
judge(answer)
this.#judgeAnswer(answer);
if(this.#answer == answer)
正解かどうか?を判定しています。
const result = document.getElementById("result");
result.innerText = tmp;
判定した結果を表示します。




戻る


著作権情報
ホームページおよプリ等に掲載されている情報等については、いかなる保障もいたしません。
ホームページおよびアプリ等を通じて入手したいかなる情報も複製、販売、出版または使用させたり、
または公開したりすることはできません。
当方は、ホームペーよびアプリ利用したいかなる理由によっての障害等が発生しても、
その結果ホームページおよびアプリ等を利用された本人または他の第三者が被った損害について
一切の責任を負わないものとします。