본문 바로가기
자바스크립트&캔버스

캔버스와 함께하는 자바스크립트, 13번째 시간 - 3D세계의 창조

1. HTML 표준 CANVAS 기술 소개 / https://itadventure.tistory.com/130

2. 자바스크립트와 CANVAS 두번째시간. 캔바스에 눈을 내리자 / https://itadventure.tistory.com/131

3. 자바스크립트와 캔버스 3번째 시간, 공튀기기 놀이 / https://itadventure.tistory.com/132

4. 자바스크립트와 캔버스 4번째 시간, 마우스의 파동을 느껴봐! | https://itadventure.tistory.com/133

5. 자바스크립트와 캔버스, 테트리스를 만들어봐-1 | https://itadventure.tistory.com/136

6. 자바스크립트와 캔버스, 테트리스를 만들어봐-2 | https://itadventure.tistory.com/139

7. 자바스크립트와 캔버스, 테트리스를 만들어봐-3 | https://itadventure.tistory.com/142

8. 자바스크립트와 캔버스, 테트리스를 만들어봐-4 | https://itadventure.tistory.com/146

9. 자바스크립트와 캔버스, 테트리스를 만들어봐-5 | https://itadventure.tistory.com/148

10. 자바스크립트와 캔버스, 테트리스를 만들어봐-6 | https://itadventure.tistory.com/152

11. 자바스크립트와 캔버스, 테트리스를 만들어봐-7 | https://itadventure.tistory.com/159

12. 자바스크립트와 캔버스, 테트리스를 만들어봐-Final | https://itadventure.tistory.com/160

13. 캔버스와 함께하는 자바스크립트, 13번째 시간 - 3D세계의 창조 

초에 하나님이 천지를 창조하시니라
땅이 혼돈하고 공허하며 흑암이 깊음 위에 있고 하나님의 신은 수면에 운행하시니라
하나님이 가라사대 빛이 있으라 하시매 빛이 있었고
그 빛이 하나님의 보시기에 좋았더라 하나님이 빛과 어두움을 나누사
빛을 낮이라 칭하시고 어두움을 밤이라 칭하시니라

성서 창세기 1장 1-5절 말씀

성서에 나오는 위 말씀은 크레이가 좋아하는 말씀 중 하나입니다.
하나님께서는 이 세상을 만드신 창조자이자 최고의 예술가이신데,
한마디로 '너무 멋지다'라고 말이 절로 나올 수 밖에 없습니다.

주제가 알맞은 음악 한곡 들으시면서 보셔도 좋으실 듯 합니다 ㅎㅎ

https://www.youtube.com/watch?v=VYkP8efNKQw

크레이에게 떠오르는 묵상은,
사람도 그 하나님의 형상대로 창조되었기 때문에, '창조'를 좋아한다는 것이지요.

예수그리스도를 주인으로 믿어 천국에 가는 자들은, 그 기쁨의 낙원에서
하나님의 창조의 능력을 일부 얻어, 작은 땅을 만들고 가꿀 수 있을지 않을지 기대해 봅니다 :)

"작은 빛아 생겨나라! 이 쪽은 뭍이 되어라! 그쪽은 호수가 되어 맑은 물로 채워지고...
노루는 이쪽 기슭에 2마리 암수 한쌍식 생겨나고 ..."

성경에 나오는 이야기는 아니고 다만 크레이의 상상력일 뿐입니다 ㅎㅎ

지난 시간까지는 캔바스라는 공간 안에 테트리스 게임을 구성하는 부분을 다루었지요?
테트리스는 2차원 공간에서 벌어지는 일이었습니다만,
이번 시간부터는 캔바스라는 공간을 3차원으로 구성하고 그 공간을 다루는 방법을 살펴보도록 하겠습니다.

아래는 캔바스를 3차원 공간으로 구성하는 기본 틀의 소스입니다.

<html>
	<head>
		<title>3차원 캔바스 틀</title>
		<style>
			body { margin: 0; }
			canvas { width: 100%; height: 100% }
		</style>
	</head>
	<body>
		<script src="https://threejs.org/build/three.min.js"></script>
		<script>
			// 3차원 세계
			var scene = new THREE.Scene();

			// 카메라 ( 카메라 수직 시야 각도, 가로세로 종횡비율, 시야거리 시작지점, 시야거리 끝지점
			var camera = new THREE.PerspectiveCamera( 75, window.innerWidth/window.innerHeight, 0.1, 1000 );

			// 렌더러 정의 및 크기 지정, 문서에 추가하기
			var renderer = new THREE.WebGLRenderer( { antialias: true, preserveDrawingBuffer: true } );
			renderer.setSize( window.innerWidth, window.innerHeight );
			
			document.body.appendChild( renderer.domElement );

            // : 초기화 영역

			var framesPerSecond=60;

			// 에니메이션 효과를 자동으로 주기 위한 보조 기능입니다.
			var animate = function () {
				// 프레임 처리
				setTimeout(function() {
					 requestAnimationFrame(animate); 
				}, 1000 / framesPerSecond);

				//    : 애니메이션 영역

				// 랜더링을 수행합니다.
				renderer.render( scene, camera );
			};

			// animate()함수를 최초에 한번은 수행해주어야 합니다.
			animate();
		</script>
	</body>
</html>

이 소스를 실행하면, 뭐가 나올까요?

화면 전체가 시꺼멓게 나오고 아무 것도 없는 상태가 됩니다.
마치 성서 창세기에 나오는 단어처럼 "공허한" 상태가 되지요..

소스 구성에 따라 3차원 공간은 준비되어 있지만, 아무 물체도 없고 빛도 없기 때문에
화면은 어떠한 흔적도 보이지 않습니다.

이제 빛을 창조해 볼까요?
초기화 영역이라는 부분이 있는데요.
이 부분에 아래 소스를 추가해 봅시다.
위치값이라는게 있는데 하나씩 익혀나갈테니 우선 넣기만 해보자구요 :)

// 빛을 생성해서
var light1 = new THREE.PointLight( 0xffffff, 1, 100 );
// 위치를 적당한 지점에 놓고
light1.position.set( 5, 5, 5 );
// 장면에 추가합니다.
scene.add( light1 );

빛이 생겨나긴 했는데, 여전히 아무것도 보이지 않습니다.
아직 물체가 없기 때문입니다.

이제 가장 단순한 도형인 정육면체를 하나 창조해 봅시다.
금방 빛을 창조한 바로 아래 공간에 위치하면 되지요.

// 정육면체 하나 만들기
var cube = new THREE.Mesh( 
	new THREE.BoxGeometry( 3, 3, 3 ), 
	new THREE.MeshStandardMaterial({ color: 0x0087E6})
);
// 생성한 모델을 장면에 추가합니다.
scene.add( cube );

그리고 하나 더 수행해야 할 부분이 있는데
시점, 즉 카메라를 뒤로 5만큼 거리를 후진해야 물체가 시야에 들어와 보입니다.

camera.position.z = 5;

시커먼 공간에 사각형 물체가 하나 보입니다.
정육면체이지만, 앞에서만 보기 때문에 사각형으로 보이는 것입니다.

정말로 정육면체인지 확인하려면 카메라를 위로 좀 올려봅시다.

camera.position.y = 2;

 

어둑어둑하지만 뭔가 입체적으로 보이는 듯하네요.
너무 어두우니 빛을 2개 더 추가해볼까요?
처음에 빛을 추가한 부분 아래에 넣어주면 됩니다.

// 빛을 또한 생성해서
var light2 = new THREE.PointLight( 0xffFFFF, 1, 100 );
// 위치를 적당한 지점에 놓고
light2.position.set( 7, -5, 6 );
// 장면에 추가합니다.
scene.add( light2 );
// 빛을 또한 생성해서
var light3 = new THREE.PointLight( 0xffFFFF, 1, 100 );
// 위치를 적당한 지점에 놓고
light3.position.set( -7, 3, 3 );
// 장면에 추가합니다.
scene.add( light3 );

 

오우, 정육면체의 모양이 뚜렷하게 보입니다.
한번 이 정육면체가 혼자 힘으로 움직이도록 생명을 불어넣어 볼까요?
소스중 애니메이션 영역에 아래 소스를 넣어봅시다.

cube.rotation.y += 0.02;

!!!
상자가 혼자서 회전하고 있습니다.
멋지지 않나요? 예제는 카메라 각도를 좀 바꿔서 위치가 다르게 보이니양해해 주세요 :)

http://dreamplan7.cafe24.com/canvas/three001.php

 

3차원 캔바스 예제 1

 

dreamplan7.cafe24.com

지금까지 보시는 모든 부분은 웹페이지에서 일어나는 일입니다.
아마도 미래에는 현실의 허공 위에 비쳐 보이는 홀로그램을 통해서
쇼핑을 할 수 있을지도 모르는 일인데요.

그 때는 이런 유사한 기술이 각광을 받을 지도 모릅니다.
3차원에 대한 개념은 차근 차근 설명드리기로 하고,
오늘은 한가지만 알고 넘어가도록 하겠습니다.

"캔버스 기술을 통하여 3차원 공간을 구현할 수 있다!"라는 점입니다.
오늘은 그러한 기술을 사용하는 기본적인 방법에 대한 '맛보기' 정도인 셈입니다.

크레이도 공부하면서 진행하는 것이라, 100% 소화한 부분만 강의로 게제하니
속도가 좀 느려도 양해 부탁드리구요 :)

자, 그러면 웹에서 사용가능한 캔버스 3차원 기술이 해외에서는 얼마나 발달했는지 한번 구경해볼까요?

https://www.youtube.com/watch?v=uTTIy7KFA8o

오늘의 전체 소스입니다.

<html>
	<head>
		<title>3차원 캔바스 예제 1</title>
		<style>
			body { margin: 0; }
			canvas { width: 100%; height: 100% }
		</style>
	</head>
	<body>
		<script src="https://threejs.org/build/three.min.js"></script>
		<script>

			// ==========================
			// 초기화 부분 시작 ( 이 부분은 문서에서 한번만 수행되면 됩니다 )
			// ==========================
			// 3차원 세계
			var scene = new THREE.Scene();

			// 카메라 ( 카메라 수직 시야 각도, 가로세로 종횡비율, 시야거리 시작지점, 시야거리 끝지점
			var camera = new THREE.PerspectiveCamera( 75, window.innerWidth/window.innerHeight, 0.1, 1000 );

			// 렌더러 정의 및 크기 지정, 문서에 추가하기
			var renderer = new THREE.WebGLRenderer( { antialias: true, preserveDrawingBuffer: true } );
			renderer.setSize( window.innerWidth, window.innerHeight );
			
			document.body.appendChild( renderer.domElement );

			// 빛을 생성해서
			var light1 = new THREE.PointLight( 0xffffff, 1, 100 );
			// 위치를 적당한 지점에 놓고
			light1.position.set( 5, 5, 5 );
			// 장면에 추가합니다.
			scene.add( light1 );

			// 빛을 또한 생성해서
			var light2 = new THREE.PointLight( 0xffFFFF, 1, 100 );
			// 위치를 적당한 지점에 놓고
			light2.position.set( 7, -5, 6 );
			// 장면에 추가합니다.
			scene.add( light2 );

			// 빛을 또한 생성해서
			var light3 = new THREE.PointLight( 0xffFFFF, 1, 100 );
			// 위치를 적당한 지점에 놓고
			light3.position.set( -7, 3, 3 );
			// 장면에 추가합니다.
			scene.add( light3 );

			// 정육면체 하나 만들기
			var cube = new THREE.Mesh( 
				new THREE.BoxGeometry( 3, 3, 3 ), 
				new THREE.MeshStandardMaterial({ color: 0x0087E6})
			);

			// 생성한 모델을 장면에 추가합니다.
			scene.add( cube );


			// 카메라의 Z좌표를 물체에서 5 정도 떨어진 지점에 위치합니다.
			camera.position.z = 5;
			camera.position.y = 2;

			// ==========================
			// 초기화 부분 끝
			// ========================== 

			var framesPerSecond=60;

			// 에니메이션 효과를 자동으로 주기 위한 보조 기능입니다.
			var animate = function () {
				// 프레임 처리
				setTimeout(function() {
					 requestAnimationFrame(animate); 
				}, 1000 / framesPerSecond);

				//    : 애니메이션 영역
				cube.rotation.y += 0.02;

				// 랜더링을 수행합니다.
				renderer.render( scene, camera );
			};

			// animate()함수를 최초에 한번은 수행해주어야 합니다.
			animate();
		</script>
	</body>
</html>

오늘도 여기까지 읽어주시느라 수고 많으셨습니다 :)
이제 개천절 휴일이군요.
좋은 시간 되시길 바라며 크레이는 이만~

 

다음강좌 보러 가기 / https://itadventure.tistory.com/45

 

3차원 공간의 개념, 캔버스와 함께하는 자바스크립트, 14번째 시간

지난 시간에는 HTML 표준 기술 캔버스에서 자바스크립트를 이용하여 3차원 모양의 정육면체를 회전시켜보는 예제를 보았었습니다 :) ​https://blog.naver.com/ephraimdrlee/221570755838 3D세계의 창조, 캔버스와..

itadventure.tistory.com