본문 바로가기
코딩과 알고리즘

3차원 웹, 밝은 빛을 보라, 캔버스와 함께하는 자바스크립트, 17번째 시간

지난 시간에는 3차원공간을 마우스로 자유자재로 돌려보는 예제를 살펴보았었는데요.

https://itadventure.tistory.com/51

 

3차원 웹, 마우스로 움직이다, 캔버스와 함께하는 자바스크립트, 16번째 시간

3차원 웹 기술, 캔버스와 자바스크립트 "마우스로 움직이다" 시간입니다 :) 오늘은 우선 예제 영상을 보도록 하실까요? ​ https://youtu.be/2ECIpZvg7Og 허공에 3개의 정육면체가 있으며, 마우스로 클릭하여 드래..

itadventure.tistory.com

박스 뒷면이 너무 새까맣게 보였던 문제에 대해 잠시 거론했었지요 :)

왜 이렇게 까말까요?

그 원인은 포인트 라이트라고 만들어 놓은 3개의 조명이 모두 Z축을 따라 양수의 방향에만 있기 때문입니다. 상자 뒷면을 비출 수 없는 위치이지요.

포인트 라이트 하나를 뒤로 가져가는 방법도 있지만 박스가 또 멀리 있으면 포인트 라이트는 아주 희미한 영향을 줄 뿐입니다.

이를 위해 준비된 조명이 있는데요 바로 전체 조명입니다.

3차원 공간 어디든 비춰주는 조명이지요.

확연한 차이를 보기 위해서, 지난번 최종 소스에서

3개의 포인트 조명을 소스에서 지워버리실까요?

// 빛을 생성해서
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 light_base = new THREE.AmbientLight( 0xf0f0f0 );
scene.add( light_base );

이제 화면을 보도록 할까요?

약간 어둑하긴 하지만 명암 차이가 없습니다.

마우스로 드래그해서 상자 뒷면도 확인해볼까요?

오, 뒷면도 깔끔합니다.

AmbieldLight는 환경조명이라고 해서 전체적인 밝기를 지정해주는 겁니다.

파라미터로는 색상코드를 주면되구요.

하지만 명암차이가 없어 빛이 들어오지 않는 실내에서 보는 느낌이군요.

이제 포인트 라이트 대신 태양광을 줘보도록 하겠습니다.

금방 추가한 부분 아래 또 다시 아래 부분을 추가해볼까요?

// 태양광을 추가합니다.
var light_sun = new THREE.DirectionalLight ( 0x808080, 3.0 );
light_sun.position.set( 1000, 1000, 3000 );
scene.add( light_sun );

 

뭔가 밝아진 느낌이지요?

상자 뒷면을 보도록 하겠습니다.

명암이 느껴지시나요?

위 아래 2개의 사진을 비교해보면 확연히 느껴지실 겁니다.

이처럼 환경조명과 태양광을 이용하면 실제에 가까운 느낌의 화면을 연출할 수 있습니다.

참고로 THREE.DirectionalLight ( 0x808080, 3.0 ); 에서 3.0 수치를 5.0이나 10.0으로 바꿔보시면 강렬한 태양빛을 구경하실 수 있을 겁니다.

오늘은 여기까지!

예제 실행페이지와 전체 소스를 공개합니다.

수고하셨습니다 :)

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

 

3차원 캔바스 예제 1

 

dreamplan7.cafe24.com

<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 src="http://fenixrepo.fao.org/cdn/js/threejs/4.4/OrbitControls.js"></script>
		<script>

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

			// 카메라 ( 카메라 수직 시야 각도, 가로세로 종횡비율, 시야거리 시작지점, 시야거리 끝지점
			var camera = new THREE.PerspectiveCamera( 45, 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 light_base = new THREE.AmbientLight( 0xf0f0f0 );
			scene.add( light_base );

			// 태양광을 추가합니다.
			var light_sun = new THREE.DirectionalLight ( 0x808080, 3.0 );
			light_sun.position.set( 1000, 1000, 3000 );
			scene.add( light_sun );

			var loader = new THREE.TextureLoader();

			// 큐브1
			var mesh;
			loader.load(
				'http://dreamplan7.cafe24.com/SL/img/%EC%B9%B4%EB%93%9C_%EC%97%B0%EB%82%A0%EB%A6%AC%EA%B8%B0.jpg', 
				function ( texture ) {
					mesh = new THREE.Mesh(
						new THREE.BoxGeometry(3, 3, 3), 
						new THREE.MeshStandardMaterial({map: texture})
					);
					scene.add(mesh);
				}
			);

			// 큐브2
			var mesh2;
			loader.load(
				'http://dreamplan7.cafe24.com/SL/img/%EC%B9%B4%EB%93%9C_%EA%B1%B4%EB%B0%98%ED%9A%A8%EA%B3%BC.jpg', 
				function ( texture ) {
					mesh2 = new THREE.Mesh(
						new THREE.BoxGeometry(3, 3, 3), 
						new THREE.MeshStandardMaterial({map: texture})
					);
					scene.add(mesh2);
					mesh2.position.set(5, 0, 0);
				}
			);

			// 큐브3
			var mesh3;
			loader.load(
				'http://dreamplan7.cafe24.com/SL/img/%EC%B9%B4%EB%93%9C_%EB%AC%B4%ED%95%9C%EC%BB%A4%ED%94%BC.jpg', 
				function ( texture ) {
					mesh3 = new THREE.Mesh(
						new THREE.BoxGeometry(3, 3, 3), 
						new THREE.MeshStandardMaterial({map: texture})
					);
					scene.add(mesh3);
					mesh3.position.set(-5, 0, 0);
				}
			);

			// 카메라의 위치 조정
			camera.position.set ( 5, 5, 7 );
			camera.lookAt(0, 0, 0);
			// camera.rotation.set ( -35 * ( Math.PI / 180 ), 35 * ( Math.PI / 180 ), 0 );
	
			// 카메라가 회전하는
			var controls = new THREE.OrbitControls (camera, renderer.domElement);
			controls.update();

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

			var framesPerSecond=60;

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

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

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