<!DOCTYPE html>
<html>
<head>
  <meta charset="utf-8">
	<title>Phasing</title>

	<meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1">
	<link rel="icon" type="image/png" sizes="174x174" href="./favicon.png">

	<script src="https://unpkg.com/@webcomponents/webcomponentsjs@^2/webcomponents-bundle.js"></script>
	<script src="../build/Tone.js"></script>
	<script src="./js/tonejs-ui.js"></script>
</head>
<body>
	<style type="text/css">
		#loop {
			margin-bottom: 10px;
			display: flex;
			background-color: #777;
			border-radius: 20px;
			padding: 10px;
		}
		tone-loop {
			flex-grow: 1;
			width: 40%;
			height: 150px;
		}
	</style>
	<tone-example>
		<tone-explanation label="Piano Phase">
			By slightly slowing down the playbackRate of the Tone.Sequence in the right channel,
			the two identical melodies phase against each other in interesting ways.
			<br><br>
			Composition by Steve Reich. Inspiration from Alexander Chen.
		</tone-explanation>

		<tone-content>
			<div id="loop">
				<tone-loop id="left" color="#7F33ED"></tone-loop>
				<tone-loop id="right" color="#1EDF3E"></tone-loop>
			</div>
			<tone-play-toggle></tone-play-toggle>
		</tone-content>
	</tone-example>

	<script type="text/javascript">
		//set the bpm and time signature first
		Tone.Transport.timeSignature = [6, 4];
		Tone.Transport.bpm.value = 180;

		//L/R channel merging
		var merge = new Tone.Merge();

		//a little reverb
		var reverb = new Tone.Freeverb({
			"roomSize" : 0.2,
			"wet" : 0.3
		});

		merge.chain(reverb, Tone.Master);

		//the synth settings
		var synthSettings = {
			"oscillator" : {
				"detune" : 0,
				"type" : "custom",
				"partials" : [2, 1, 2, 2],
				"phase" : 0,
				"volume" : 0
			},
			"envelope" : {
				"attack" : 0.005,
				"decay" : 0.3,
				"sustain" : 0.2,
				"release" : 1,
			},
			"portamento" : 0.01,
			"volume" : -20
		};

		//left and right synthesizers
		var synthL = new Tone.Synth(synthSettings).connect(merge.left);
		var synthR = new Tone.Synth(synthSettings).connect(merge.right);

		//the two Tone.Sequences
		var partL = new Tone.Sequence(function(time, note){
			synthL.triggerAttackRelease(note, "8n", time);
		}, ["E4", "F#4", "B4", "C#5", "D5", "F#4", "E4", "C#5", "B4", "F#4", "D5", "C#5"], "8n").start();

		var partR = new Tone.Sequence(function(time, note){
			synthR.triggerAttackRelease(note, "8n", time);
		}, ["E4", "F#4", "B4", "C#5", "D5", "F#4", "E4", "C#5", "B4", "F#4", "D5", "C#5"], "8n").start("2m");
		
		//set the playback rate of the right part to be slightly slower
		partR.playbackRate = 0.985;

		document.querySelector("tone-play-toggle").bind(Tone.Transport);
		document.querySelector("#left").bind(partL);
		document.querySelector("#right").bind(partR);
		/*// GUI //

		Interface.Button({
			key : 32,
			type : "toggle",
			text : "Start",
			activeText : "Stop",
			start : function(){
				Tone.Transport.start("+0.1");
			},
			end : function(){
				Tone.Transport.stop();
			}
		});

		//draw two circles
		var leftCanvas = $("#Left");
		var rightCanvas = $("#Right");
		var leftContext = leftCanvas.get(0).getContext("2d");
		var rightContext = rightCanvas.get(0).getContext("2d");
		var canvasWidth = leftCanvas.width() * 2;
		var canvasHeight = leftCanvas.height() * 2;
		var radius = Math.min(canvasWidth, canvasHeight);

		function sizeCanvas(){
			canvasWidth = leftCanvas.width() * 2;
			canvasHeight = leftCanvas.height() * 2;
			radius = Math.min(canvasWidth, canvasHeight) * 0.8;

			leftContext.canvas.width = canvasWidth;
			leftContext.canvas.height = canvasHeight;

			rightContext.canvas.width = canvasWidth;
			rightContext.canvas.height = canvasHeight;
		}

		$(window).on("resize", sizeCanvas);

		sizeCanvas();

		var twoPi = Math.PI * 2;

		function loop(){
			requestAnimationFrame(loop);
			leftContext.lineWidth = radius * 0.1;
			rightContext.lineWidth = radius * 0.1;
			//draw the left progress
			leftContext.clearRect(0, 0, canvasWidth, canvasHeight);
			leftContext.strokeStyle = "#7F33ED";
			leftContext.save();
			leftContext.translate(canvasWidth / 2, canvasHeight / 2);
			leftContext.rotate(-Math.PI / 2);
			leftContext.beginPath();
			leftContext.arc(0, 0, radius/2, 0, twoPi * partL.progress, false);
			leftContext.stroke();
			leftContext.restore();

			//draw the left progress
			rightContext.clearRect(0, 0, canvasWidth, canvasHeight);
			rightContext.strokeStyle = "#1EDF3E";
			rightContext.save();
			rightContext.translate(canvasWidth / 2, canvasHeight / 2);
			rightContext.rotate(-Math.PI / 2);
			rightContext.beginPath();
			rightContext.arc(0, 0, radius/2, 0, twoPi * partR.progress, false);
			rightContext.stroke();
			rightContext.restore();
		}
		loop();*/
		
	</script>
</body>
</html>