BabylonJS-메시
이 장에서는 메쉬 빌더를 사용하여 다양한 모양을 만드는 방법을 배웁니다. 이전 장에서 모양을 만드는 방법을 이미 배웠습니다.
차이점은 meshbuilder를 사용하면 모양에 색상, 이미지를 유연하게 추가 할 수 있다는 것입니다.
MeshBuilder를 사용하는 CreateBox
이제 MeshBuilder를 사용하여 상자를 만드는 방법을 살펴 보겠습니다.
데모
<!doctype html>
<html>
<head>
<meta charset = "utf-8">
<title>BabylonJs - Basic Element-Creating Scene</title>
<script src = "babylon.js"></script>
<style>
canvas {width: 100%; height: 100%;}
</style>
</head>
<body>
<canvas id = "renderCanvas"></canvas>
<script type = "text/javascript">
var canvas = document.getElementById("renderCanvas");
var engine = new BABYLON.Engine(canvas, true);
var createScene = function() {
var scene = new BABYLON.Scene(engine);
scene.clearColor = new BABYLON.Color3(0, 0, 1);
var camera = new BABYLON.ArcRotateCamera("Camera", 1, 0.8, 10, new BABYLON.Vector3(0, 0, 0), scene);
camera.attachControl(canvas, true);
var light = new BABYLON.HemisphericLight("light1", new BABYLON.Vector3(0, 1, 0), scene);
light.intensity = 0.7;
var pl = new BABYLON.PointLight("pl", BABYLON.Vector3.Zero(), scene);
pl.diffuse = new BABYLON.Color3(1, 1, 1);
pl.specular = new BABYLON.Color3(1, 1, 1);
pl.intensity = 0.8;
var mat = new BABYLON.StandardMaterial("mat1", scene);
mat.alpha = 1.0;
mat.diffuseColor = new BABYLON.Color3(0, 1, 0);
var texture = new BABYLON.Texture("images/cube.png", scene);
mat.diffuseTexture = texture;
var hSpriteNb = 3; // 3 sprites per raw
var vSpriteNb = 2; // 2 sprite raws
var faceUV = new Array(6);
for (var i = 0; i < 6; i++) {
faceUV[i] = new BABYLON.Vector4(i/hSpriteNb, i/vSpriteNb, (i+1)/hSpriteNb, (i+1)/vSpriteNb);
}
var options = {
width: 1.5,
height: 1.5,
depth: 1.5,
faceUV: faceUV
};
var box = BABYLON.MeshBuilder.CreateBox("box", options, scene);
box.material = mat;
scene.registerBeforeRender(function() {
pl.position = camera.position;
});
return scene;
};
var scene = createScene();
engine.runRenderLoop(function() {
scene.render();
});
</script>
</body>
</html>
산출
위의 코드 줄은 다음 출력을 생성합니다.
위의 예에서는 아래와 같이 스프라이트 이미지를 사용했습니다. 가로로 3 개의 열과 세로로 2 개의 행이 있습니다.
이 데모에서는 cube.png라는 이미지를 사용했습니다. 이미지는 로컬로 images / 폴더에 저장되며 참조를 위해 아래에 붙여 넣습니다. cube.png는 스프라이트 이미지이고 스프라이트 이미지는 이미지 모음입니다. 우리는 큐브에 이미지를 보여주고 싶었 기 때문에 큐브의 모든면을 모으고 싶었습니다. 선택한 유사한 스프라이트 이미지를 다운로드하여 데모 링크에서 사용할 수도 있습니다.
createBox 빌더는 크기에 대한 옵션을 제공합니다.
예를 들면
var box = BABYLON.MeshBuilder.CreateBox("box", options, scene);
데모
var hSpriteNb = 3; // 3 sprites per raw ie colums horizontally as shown in the image
var vSpriteNb = 2; // 2 sprite raws as shown in the image above.
var faceUV = new Array(6); // the cube has 6 sides so creating array for same.
for (var i = 0; i < 6; i++) {
faceUV[i] = new BABYLON.Vector4(i/hSpriteNb, i/vSpriteNb, (i+1)/hSpriteNb, (i+1)/vSpriteNb);
}
var options = {
width: 1.5,
height: 1.5,
depth: 1.5,
faceUV: faceUV
};
이것은 createBox 메서드를 사용하여 meshbuilder에 텍스처를 적용하는 것입니다. cube.png 가로로 3 개의 열과 세로로 2 개의 행이있는 큐브 또는 상자에는 6 개의면이 있습니다.
텍스처를 적용하기 위해 옵션 매개 변수를 사용합니다.
Var box = BABYLON.MeshBuilder.CreateBox ('box', options, scene);
우리는 육면체의 측면 인 크기가 6 인 faceUV라는 배열을 정의했습니다. 이 배열에는 항상 Vector4 요소가 있습니다. 각 Vector4 (x, y, z, w)는 다음과 같이 정의됩니다.
- x = Ubottom
- y = Vbottom
- z = Utop
- w = Vtop
벡터는 [0, 1] 범위에 있습니다. Ubottom과 Vbottom은 텍스처 자르기가 시작되는 왼쪽 하단 지점의 2D 좌표입니다. Utop, Vtop은 텍스처 자르기가 끝나는 오른쪽 상단 지점입니다.
var hSpriteNb = 3; // 3 sprites per raw
var vSpriteNb = 2; // 2 sprite raws
var faceUV = new Array(6);
for (var i = 0; i < 6; i++) {
faceUV[i] = new BABYLON.Vector4(i/hSpriteNb, i/vSpriteNb, (i+1)/hSpriteNb, (i+1)/vSpriteNb);
}
기본 텍스처, 즉 주어진 이미지가 상자의 모든면에 적용된다고 가정합니다. 상자의 한면 또는 한 면만 변경하려면 아래와 같이 값을 직접 할당 할 수 있습니다.
var hSpriteNb = 3; // 3 sprites per raw
var vSpriteNb = 2; // 2 sprite raws
var faceUV = new Array(6);
faceUV[4] = new BABYLON.Vector4(0, 0, 1/hSpriteNb, 1/vSpriteNb);
예
<!doctype html>
<html>
<head>
<meta charset = "utf-8">
<title>BabylonJs - Basic Element-Creating Scene</title>
<script src = "babylon.js"></script>
<style>
canvas {width: 100%; height: 100%;}
</style>
</head>
<body>
<canvas id = "renderCanvas"></canvas>
<script type = "text/javascript">
var canvas = document.getElementById("renderCanvas");
var engine = new BABYLON.Engine(canvas, true);
var createScene = function() {
var scene = new BABYLON.Scene(engine);
scene.clearColor = new BABYLON.Color3(0, 0, 1);
var camera = new BABYLON.ArcRotateCamera("Camera", 1, 0.8, 10, new BABYLON.Vector3(0, 0, 0), scene);
camera.attachControl(canvas, true);
var light = new BABYLON.HemisphericLight("light1", new BABYLON.Vector3(0, 1, 0), scene);
light.intensity = 0.7;
var pl = new BABYLON.PointLight("pl", BABYLON.Vector3.Zero(), scene);
pl.diffuse = new BABYLON.Color3(1, 1, 1);
pl.specular = new BABYLON.Color3(1, 1, 1);
pl.intensity = 0.8;
var mat = new BABYLON.StandardMaterial("mat1", scene);
mat.alpha = 1.0;
mat.diffuseColor = new BABYLON.Color3(0.8, 0.8, 0.8);
var texture = new BABYLON.Texture("images/3d.png", scene);
mat.diffuseTexture = texture;
var hSpriteNb = 3; // 3 sprites per raw
var vSpriteNb = 2; // 2 sprite raws
var faceUV = new Array(6);
faceUV[4] = new BABYLON.Vector4(0, 0, 1/hSpriteNb, 1/vSpriteNb);
var options = {
width:3,
height:3,
depth: 3,
faceUV:faceUV
};
var box = BABYLON.MeshBuilder.CreateBox("box", options, scene);
box.material = mat;
scene.registerBeforeRender(function() {
pl.position = camera.position;
});
return scene;
};
var scene = createScene();
engine.runRenderLoop(function() {
scene.render();
});
</script>
</body>
</html>
산출
위의 코드 줄은 다음 출력을 생성합니다.
이 데모에서는 3d.png라는 이미지를 사용했습니다. 이미지는 로컬로 images / 폴더에 저장되며 참조를 위해 아래에 붙여 넣습니다. 3d.png는 스프라이트 이미지입니다. 스프라이트 이미지는 이미지 모음입니다. 큐브의 모든면이 함께있는 큐브에 이미지를 표시하고 싶었습니다. 선택한 유사한 스프라이트 이미지를 다운로드하여 데모 링크에서 사용할 수도 있습니다.
상자에 사용되는 텍스처 − images/3d.png
MeshCylinder
이 섹션에서는 MeshCylinder를 만드는 방법을 살펴 봅니다.
MeshCylinder를 생성하려면 BABYLON.MeshBuilder.CreateCylinder 클래스를 사용해야합니다.
클래스의 매개 변수는 다음과 같습니다.
var meshcylinder = BABYLON.MeshBuilder.CreateCylinder("meshcylinder", {
height: 3,
diameter: 35,
tessellation: 52
}, scene);
메쉬를 사용하는 CreateCylinder와 meshbuilder의 차이점은 meshbuilder에서 옵션을 사용할 수 있다는 것입니다. 지금 우리는 실린더로 전달되는 옵션으로 높이, 직경 및 테셀레이션을 사용하고 있습니다. 이 메쉬의 재질로 와이어 프레임이있는 표준 재질을 사용하고 있습니다. 브라우저에서 출력을 확인하고 실린더를 확인하십시오. 게임에서 유사한 구조를 장면에서 회전하는 바퀴로 사용할 수 있습니다.
데모
<!doctype html>
<html>
<head>
<meta charset = "utf-8">
<title>Babylon.js demo - Mesh Builder</title>
<script src = "babylon.js"></script>
<style>
html,body,canvas { margin: 0; padding: 0; width: 100%; height: 100%; font-size: 0; }
</style>
</head>
<body>
<canvas id = "renderCanvas"></canvas>
<script type = "text/javascript">
var canvas = document.getElementById("renderCanvas");
var engine = new BABYLON.Engine(canvas, true);
var createScene = function() {
var scene = new BABYLON.Scene(engine);
scene.clearColor = new BABYLON.Color3(0.8, 0.8, 0.8);
var camera = new BABYLON.ArcRotateCamera("Camera", -Math.PI / 6, 1.3, 40, new BABYLON.Vector3(0, -3, 0), scene);
var light = new BABYLON.HemisphericLight("hemi", new BABYLON.Vector3(0, 1, 0), scene);
var mat = new BABYLON.StandardMaterial("mat", scene);
mat.diffuseColor = new BABYLON.Color3(0.1, .5, 0);
mat.specularColor = new BABYLON.Color3(0, 0, 0);
mat.wireframe = true;
var meshcylinder = BABYLON.MeshBuilder.CreateCylinder("meshcylinder", {
height: 3,
diameter: 35,
tessellation: 52
}, scene);
meshcylinder.material = mat;
meshcylinder.position = new BABYLON.Vector3(0, 0, 0);
scene.activeCamera.attachControl(canvas);
return scene;
};
var scene = createScene();
engine.runRenderLoop(function() {
scene.render();
});
</script>
</body>
</html>
산출
위의 코드 줄은 다음 출력을 생성합니다.
이제 메시 빌더로 만든 여러 모양이 하나의 데모에서 함께 사용됩니다. 아래 데모 링크에서 다루는 모양은 다음 섹션에 나열됩니다.
Ground
Cone
Plane
Disc
Torus
Polyhedron
IcoSphere
BabylonJS – 메시 교차점 및 점
게임에서 두 개체가 교차 할 때 수행해야하는 작업을 알고 있으므로 게임에서 메시 교차가 중요합니다. 메시가 교차 할 때 캡처해야하는 이벤트에 대한 동일한 개념이 아래 데모에서 설명됩니다.
아래의 데모에서 우리는 다음 두 가지 개념을 다루었습니다.
- 메시 교차
- 교차점
<!doctype html>
<html>
<head>
<meta charset = "utf-8">
<title>BabylonJs - Basic Element-Creating Scene</title>
<script src = "babylon.js"></script>
<style>
canvas {width: 100%; height: 100%;}
</style>
</head>
<body>
<canvas id = "renderCanvas"></canvas>
<script type = "text/javascript">
var canvas = document.getElementById("renderCanvas");
var engine = new BABYLON.Engine(canvas, true);
var createScene = function() {
var scene = new BABYLON.Scene(engine);
scene.clearColor = new BABYLON.Color3(1, 1, 1);
var camera = new BABYLON.ArcRotateCamera("ArcRotateCamera", 1, 0.8, 20, new BABYLON.Vector3(0, 0, 0), scene);
camera.attachControl(canvas, true);
var matcone = new BABYLON.StandardMaterial("mat1", scene);
matcone.alpha = 1.0;
matcone.diffuseColor = new BABYLON.Color3(0, 0, 0);
matcone.wireframe = true;
var cone = BABYLON.MeshBuilder.CreateCylinder("cone", {height : 10, diameterTop: 10,diameterBottom:10, tessellation: 5}, scene);
cone.position= new BABYLON.Vector3(12,1,0);
cone.material = matcone;
var balloon1 = BABYLON.Mesh.CreateSphere("balloon1",5, 1.0, scene);
var balloon2 = BABYLON.Mesh.CreateSphere("balloon2", 5, 1.0, scene);
var balloon3 = BABYLON.Mesh.CreateSphere("balloon3", 5, 1.0, scene);
balloon1.material = new BABYLON.StandardMaterial("matBallon", scene);
balloon2.material = new BABYLON.StandardMaterial("matBallon", scene);
balloon3.material = new BABYLON.StandardMaterial("matBallon", scene);
balloon1.position = new BABYLON.Vector3(4, 2, 0);
balloon2.position = new BABYLON.Vector3(5, 1, 0);
balloon3.position = new BABYLON.Vector3(7, 0, 0);
var pointToIntersect = new BABYLON.Vector3(10, 0, 0);
var a = 0.01;
scene.registerBeforeRender(function () {
if (balloon1.intersectsMesh(cone, false)) {
balloon1.material.emissiveColor = new BABYLON.Color3(1, 0, 0);
} else {
balloon1.material.emissiveColor = new BABYLON.Color3(0, 1, 0);
}
if (balloon2.intersectsMesh(cone, false)) {
balloon2.material.emissiveColor = new BABYLON.Color3(1, 0, 0);
} else {
balloon2.material.emissiveColor = new BABYLON.Color3(0, 1, 0);
}
if (balloon3.intersectsMesh(cone, false)) {
balloon3.material.emissiveColor = new BABYLON.Color3(1, 0, 0);
} else {
balloon3.material.emissiveColor = new BABYLON.Color3(0, 1, 0);
}
if (balloon3.intersectsPoint(pointToIntersect)) {
balloon3.material.emissiveColor = new BABYLON.Color3(0, 0, 0);
}
a += 0.01;
balloon1.position.x += Math.cos(a) / 10;
balloon2.position.x += Math.cos(a) / 10;
balloon3.position.x += Math.cos(a) / 10;
});
return scene;
};
var scene = createScene();
engine.runRenderLoop(function() {
scene.render();
});
</script>
</body>
</html>
산출
위의 코드는 다음 출력을 생성합니다.
설명
위의 코드를 사용하여 와이어 프레임이 참인 실린더를 만들었습니다. 우리는 3 개의 구체를 만들었습니다. 구의 원래 색상은 녹색입니다.
에서 scene.registerBeforeRender 여기서 원통 인 메시와의 교차점을 기준으로 구의 색상을 변경합니다.
다음 코드를 고려하십시오. registerBeforeRender −
if (balloon1.intersectsMesh(cone, false)) {
balloon1.material.emissiveColor = new BABYLON.Color3(1, 0, 0);
} else {
balloon1.material.emissiveColor = new BABYLON.Color3(0, 1, 0);
}
intersectsMesh 전달 된 매개 변수에 지정된 메시와 교차하는 경우 true 또는 false를 제공합니다.
예를 들면
balloon1.intersectsMesh(cone, false); //cone refers to the cylinder mesh here.
구의 색상은 원통과 교차하는 빨간색으로 변경됩니다. 그렇지 않으면 녹색입니다.
다음 코드는 교차하는 지점에 사용됩니다-
var pointToIntersect = new BABYLON.Vector3(10, 0, 0);
if (balloon3.intersectsPoint(pointToIntersect)) {
balloon3.material.emissiveColor = new BABYLON.Color3(0, 0, 0);
}
여기, pointtoIntersect변수는 x 축에서 10 인 위치 벡터입니다. 구가 교차점을 교차하면 구의 색상이 검은 색으로 변경됩니다.
BabylonJS – MeshPicking 충돌
충돌을 선택하면 실제로 좌표가 제공되며 그 위치에 메시를 배치 할 수 있습니다. 개체는 마우스로 선택되며 마우스로 클릭 한 위치에 놓을 수 있습니다. 사용자가 마우스를 클릭 한 위치에 메시 (개체)를 배치해야합니다. 따라서 충돌 선택의 도움으로 클릭 한 위치의 좌표를 확인하는 데 도움이됩니다.
데모
<!doctype html>
<html>
<head>
<meta charset = "utf-8">
<title>BabylonJs - Basic Element-Creating Scene</title>
<script src = "babylon.js"></script>
<style>
canvas {width: 100%; height: 100%;}
</style>
</head>
<body>
<canvas id = "renderCanvas"></canvas>
<script type = "text/javascript">
var canvas = document.getElementById("renderCanvas");
var engine = new BABYLON.Engine(canvas, true);
var createScene = function() {
var scene = new BABYLON.Scene(engine);
scene.clearColor = new BABYLON.Color3(1, 1, 1);
// setup environment
var light0 = new BABYLON.PointLight("Omni", new BABYLON.Vector3(0, 10, 20), scene);
var freeCamera = new BABYLON.FreeCamera("FreeCamera", new BABYLON.Vector3(0, 0, -30), scene);
var balloon1 = BABYLON.Mesh.CreateSphere("balloon1",5, 1.0, scene);
var balloon2 = BABYLON.Mesh.CreateSphere("balloon2", 5, 1.0, scene);
balloon1.material = new BABYLON.StandardMaterial("matBallon", scene);
balloon2.material = new BABYLON.StandardMaterial("matBallon", scene);
balloon1.position = new BABYLON.Vector3(0, 0, -0.1);
balloon2.position = new BABYLON.Vector3(0, 0, -0.1);
balloon1.material.emissiveColor = new BABYLON.Color3(1, 0, 0);
balloon2.material.emissiveColor = new BABYLON.Color3(0, 0, 1);
//Wall
var wall = BABYLON.Mesh.CreatePlane("wall", 30.0, scene);
wall.material = new BABYLON.StandardMaterial("wallMat", scene);
wall.material.emissiveColor = new BABYLON.Color3(0.5, 1, 0.5);
//When pointer down event is raised
scene.onPointerDown = function (evt, pickResult) {
// if the click hits the ground object, we change the impact position
if (pickResult.hit) {
var dateValue = new Date();
var secondNumber = dateValue.getSeconds();
if (secondNumber % 2 == 0) {
balloon1.position.x = pickResult.pickedPoint.x;
balloon1.position.y = pickResult.pickedPoint.y;
} else {
balloon2.position.x = pickResult.pickedPoint.x;
balloon2.position.y = pickResult.pickedPoint.y;
}
}
};
return scene;
};
var scene = createScene();
engine.runRenderLoop(function() {
scene.render();
});
</script>
</body>
</html>
산출
설명
위의 예에서는 하나의 평면과 2 개의 구를 사용했습니다. 이 출력을 생성하려면 다음 코드를 사용하십시오.
scene.onPointerDown = function (evt, pickResult) {
// if the click hits the ground object, we change the impact position
if (pickResult.hit) {
var dateValue = new Date();
var secondNumber = dateValue.getSeconds();
if (secondNumber % 2 == 0) {
balloon1.position.x = pickResult.pickedPoint.x;
balloon1.position.y = pickResult.pickedPoint.y;
} else {
balloon2.position.x = pickResult.pickedPoint.x;
balloon2.position.y = pickResult.pickedPoint.y;
}
}
};
이벤트 scene.onPointerDown 좌표 -x, y 및 z를 제공합니다. pickResult.
그라운드 메쉬를 클릭하면 pickResult.hit이 true로 제공됩니다. 홀수 / 짝수 초를 고려하고 구의 위치를 변경하여 위와 같이 결과 z 및 y 좌표를 선택합니다. 위치가 변경되면 마우스를 클릭하고 배치하는 위치에 구가 배치됩니다. 위의 데모를 동일하게 시도 할 수 있습니다.
BabylonJS – Raycast
Raycast는 태양 광선과 같으며 장면에서 충돌 및 교차를 확인하는 데 사용됩니다.
통사론
var ray = new BABYLON.Ray(origin, direction, length);
매개 변수
레이 캐스트에 대한 다음 매개 변수를 고려하십시오.
Origin − 광선이 시작될 위치.
Direction − 광선 방향은 다음과 같이 계산됩니다. −
var forward = new BABYLON.Vector3(0,0,1);
forward = vecToLocal(forward, box);
var direction = forward.subtract(origin);
그런 다음 방향을 얻기 위해 원점 인 상자 위치에서 방향을 뺍니다.
Length − 광선의 길이.
데모
<!doctype html>
<html>
<head>
<meta charset = "utf-8">
<title>BabylonJs - Basic Element-Creating Scene</title>
<script src = "babylon.js"></script>
<style>
canvas {width: 100%; height: 100%;}
</style>
</head>
<body>
<canvas id = "renderCanvas"></canvas>
<script type = "text/javascript">
var canvas = document.getElementById("renderCanvas");
var engine = new BABYLON.Engine(canvas, true);
var createScene = function() {
var scene = new BABYLON.Scene(engine);
var light = new BABYLON.PointLight("Omni", new BABYLON.Vector3(0, 100, 100), scene);
var camera = new BABYLON.ArcRotateCamera("Camera", 0, 0.8, 100, new BABYLON.Vector3.Zero(), scene);
camera.attachControl(canvas, true);
var ground = BABYLON.Mesh.CreateGround("ground", 500, 500, 10, scene);
var box = BABYLON.Mesh.CreateBox("box", 4.0, scene);
box.position.y = 2;
box.scaling.z = 2;
var matBox = new BABYLON.StandardMaterial("matBox", scene);
matBox.diffuseColor = new BABYLON.Color3(0.8, 0.1, 0.5);
box.material = matBox;
box.isPickable = false;
var box2 = BABYLON.Mesh.CreateBox("box2", 8.0, scene);
box2.position = new BABYLON.Vector3(-20, 4, 0);
var matBox2 = new BABYLON.StandardMaterial("matBox2", scene);
matBox2.diffuseColor = new BABYLON.Color3(1, 0, 0);
box2.material = matBox2;
var box3 = BABYLON.Mesh.CreateBox("box3", 8.0, scene);
box3.position = new BABYLON.Vector3(20, 4, 0);
var matBox3 = new BABYLON.StandardMaterial("matBox3", scene);
matBox3.diffuseColor = new BABYLON.Color3(1, 0, 0);
box3.material = matBox3;
var box4 = BABYLON.Mesh.CreateBox("box4", 8.0, scene);
box4.position = new BABYLON.Vector3(0, 0, 20);
var matBox4 = new BABYLON.StandardMaterial("matBox4", scene);
matBox4.diffuseColor = new BABYLON.Color3(0, 1, 0);
box4.material = matBox4;
var box5 = BABYLON.Mesh.CreateBox("box5", 8.0, scene);
box5.position = new BABYLON.Vector3(0, 0, -20);
var matBox5 = new BABYLON.StandardMaterial("matBox5", scene);
matBox5.diffuseColor = new BABYLON.Color3(0, 1, 0);
box5.material = matBox5;
function mousemovef() {
var pickResult = scene.pick(scene.pointerX, scene.pointerY);
if (pickResult.hit) {
var diffX = pickResult.pickedPoint.x - box.position.x;
var diffY = pickResult.pickedPoint.z - box.position.z;
box.rotation.y = Math.atan2(diffX,diffY);
}
}
scene.onPointerMove = function () {
mousemovef();
};
function vecToLocal(vector, mesh) {
var m = mesh.getWorldMatrix();
var v = BABYLON.Vector3.TransformCoordinates(vector, m);
return v;
}
scene.registerBeforeRender(function () {
var origin = box.position;
var forward = new BABYLON.Vector3(0,0,1);
forward = vecToLocal(forward, box);
var direction = forward.subtract(origin);
direction = BABYLON.Vector3.Normalize(direction);
var length = 100;
var ray = new BABYLON.Ray(origin, direction, length);
// ray.show(scene, new BABYLON.Color3(1, 1, 0.1));
var hit = scene.pickWithRay(ray);
if (hit.pickedMesh) {
hit.pickedMesh.scaling.y += 0.01;
}
});
return scene;
};
var scene = createScene();
engine.runRenderLoop(function() {
scene.render();
});
</script>
</body>
</html>
산출
위의 코드 줄은 다음 출력을 생성합니다.
설명
중앙에 레이 캐스트 역할을하는 메인 박스가 있습니다. 상자를 가리키면 상자의 크기가 커집니다. 이 개념은 게임을 할 때 어떤 다른 물체가 접촉하고 필요한 조치를 취할 수 있는지 알기 위해 유용합니다.
첨가 box.isPickable = false;중앙의 메인 박스는 고려되지 않습니다. 광선에 어떤 물체도 포함되지 않도록하려면 다음을 추가하십시오.box.isPickable = false; 그것에.
다음 코드는 광선이 선택한 상자의 배율을 추가합니다.
scene.registerBeforeRender(function () {
var origin = box.position;
var forward = new BABYLON.Vector3(0,0,1);
forward = vecToLocal(forward, box);
var direction = forward.subtract(origin);
direction = BABYLON.Vector3.Normalize(direction);
var length = 100;
var ray = new BABYLON.Ray(origin, direction, length);
var hit = scene.pickWithRay(ray);
if (hit.pickedMesh) {
hit.pickedMesh.scaling.y += 0.01;
}
});
var ray = new BABYLON.Ray(origin, direction, length); 광선을 만들고 기본 상자 위치를 원점으로 사용합니다.
광선 방향은 다음과 같이 계산됩니다.
var forward = new BABYLON.Vector3(0,0,1);
forward = vecToLocal(forward, box);
var direction = forward.subtract(origin);
그런 다음 방향을 얻기 위해 원점 인 상자 위치에서 방향을 뺍니다. 함수vecToLocal 벡터에 메시 행렬을 곱하여 메시 시점에서 위치를 변환하도록 설계되었습니다.
광선에서 히트 포인트를 얻습니다. var hit = scene.pickWithRay(ray);
광선이 메시와 일치하는 위치를 제공합니다.
스케일링은 다음 코드 줄을 실행하여 선택한 메쉬에 적용됩니다.
if (hit.pickedMesh) {
hit.pickedMesh.scaling.y += 0.01;
}
출력을 보려면 브라우저에서 위의 예를 시도하십시오.
술어 함수가있는 Raycast
이제 predicate 함수가있는 raycast가 작동하는 방식과 rayhelper로 표시되는 방향을 살펴 보겠습니다.
데모
<!doctype html>
<html>
<head>
<meta charset = "utf-8">
<title>BabylonJs - Basic Element-Creating Scene</title>
<script src = "babylon.js"></script>
<style>
canvas {width: 100%; height: 100%;}
</style>
</head>
<body>
<canvas id = "renderCanvas"></canvas>
<script type = "text/javascript">
var canvas = document.getElementById("renderCanvas");
var engine = new BABYLON.Engine(canvas, true);
var createScene = function() {
var scene = new BABYLON.Scene(engine);
var light = new BABYLON.PointLight("Omni", new BABYLON.Vector3(0, 100, 100), scene);
var camera = new BABYLON.ArcRotateCamera("Camera", 0, 0.8, 100, new BABYLON.Vector3.Zero(), scene);
camera.attachControl(canvas, true);
var ground = BABYLON.Mesh.CreateGround("ground", 500, 500, 10, scene);
var box = BABYLON.Mesh.CreateBox("box", 4.0, scene);
box.position.y = 2;
box.scaling.z = 2;
var matBox = new BABYLON.StandardMaterial("matBox", scene);
matBox.diffuseColor = new BABYLON.Color3(0.8, 0.1, 0.5);
box.material = matBox;
box.isPickable = false;
var box2 = BABYLON.Mesh.CreateBox("box2", 8.0, scene);
box2.position = new BABYLON.Vector3(-20, 4, 0);
var matBox2 = new BABYLON.StandardMaterial("matBox2", scene);
matBox2.diffuseColor = new BABYLON.Color3(1, 0, 0);
box2.material = matBox2;
var box3 = BABYLON.Mesh.CreateBox("box3", 8.0, scene);
box3.position = new BABYLON.Vector3(20, 4, 0);
var matBox3 = new BABYLON.StandardMaterial("matBox3", scene);
matBox3.diffuseColor = new BABYLON.Color3(1, 0, 0);
box3.material = matBox3;
var box4 = BABYLON.Mesh.CreateBox("box4", 8.0, scene);
box4.position = new BABYLON.Vector3(0, 0, 20);
var matBox4 = new BABYLON.StandardMaterial("matBox4", scene);
matBox4.diffuseColor = new BABYLON.Color3(0, 1, 0);
box4.material = matBox4;
var box5 = BABYLON.Mesh.CreateBox("box5", 8.0, scene);
box5.position = new BABYLON.Vector3(0, 0, -20);
var matBox5 = new BABYLON.StandardMaterial("matBox5", scene);
matBox5.diffuseColor = new BABYLON.Color3(0, 1, 0);
box5.material = matBox5;
//ray showing the direction
var ray = new BABYLON.Ray();
var rayHelper = new BABYLON.RayHelper(ray);
var localMeshDirection = new BABYLON.Vector3(0, 0, -1);
var localMeshOrigin = new BABYLON.Vector3(0, 0, -.4);
var length = 10;
rayHelper.attachToMesh(box, localMeshDirection, localMeshOrigin, length);
rayHelper.show(scene);
function mousemovef() {
var pickResult = scene.pick(scene.pointerX, scene.pointerY);
if (pickResult.hit) {
var diffX = pickResult.pickedPoint.x - box.position.x;
var diffY = pickResult.pickedPoint.z - box.position.z;
box.rotation.y = Math.atan2(diffX,diffY);
}
}
scene.onPointerMove = function () {
mousemovef();
};
function vecToLocal(vector, mesh) {
var m = mesh.getWorldMatrix();
var v = BABYLON.Vector3.TransformCoordinates(vector, m);
return v;
}
scene.registerBeforeRender(function () {
var origin = box.position;
function predicate(mesh) {
if (mesh == box2 || mesh == box || mesh == box5) {
return false;
}
return true;
}
var forward = new BABYLON.Vector3(0,0,1);
forward = vecToLocal(forward, box);
var direction = forward.subtract(origin);
direction = BABYLON.Vector3.Normalize(direction);
var length = 100;
var ray = new BABYLON.Ray(origin, direction, length);
// ray.show(scene, new BABYLON.Color3(1, 1, 0.1));
var hit = scene.pickWithRay(ray, predicate);
if (hit.pickedMesh) {
hit.pickedMesh.scaling.y += 0.01;
}
});
return scene;
};
var scene = createScene();
engine.runRenderLoop(function() {
scene.render();
});
</script>
</body>
</html>
산출
위의 코드 줄은 다음 출력을 생성합니다.
설명
술어 함수가있는 Raycast는 원하는 메시를 선택하는 데 도움이됩니다. 메시를 선택하지 않으려면 동일한 항목을 무시할 수 있습니다.
function predicate(mesh) {
if (mesh == box2 || mesh == box || mesh == box5) {
return false;
}
return true;
}
위의 기능은 광선에 의해 선택된 메쉬를 제공합니다. 선택된 메쉬가 box2, box 또는 box5이면 false를 반환합니다. 그렇지 않으면 사실입니다.
위의 예를 동일하게 시도 할 수 있습니다.
BabylonJS – 메시 섀도우
그림자는 생성 된 메시에 빛이 떨어지는 방식에 따라 렌더링됩니다. 3D 세계에서 결과물이 사실적으로 보이도록 만드는 데 중요한 역할을합니다.
이제 babylonjs를 사용하여 그림자를 만드는 방법을 알아 보겠습니다.
통사론
var shadowGenerator00 = new BABYLON.ShadowGenerator(shadowsize, light);
매개 변수
메쉬 그림자와 관련된 다음 매개 변수를 고려하십시오.
Shadowsize − 그림자의 크기.
Light − 장면에 사용 된 빛.
데모
<!doctype html>
<html>
<head>
<meta charset = "utf-8">
<title>BabylonJs - Basic Element-Creating Scene</title>
<script src = "babylon.js"></script>
<style>
canvas {width: 100%; height: 100%;}
</style>
</head>
<body>
<canvas id = "renderCanvas"></canvas>
<script type = "text/javascript">
var canvas = document.getElementById("renderCanvas");
var engine = new BABYLON.Engine(canvas, true);
var createScene = function() {
var scene = new BABYLON.Scene(engine);
scene.clearColor = new BABYLON.Color3(1, 1, 1);
var camera = new BABYLON.ArcRotateCamera("ArcRotateCamera", 1, 0.8, 20, new BABYLON.Vector3(0, 0, 0), scene);
camera.attachControl(canvas, true);
// light1
var light = new BABYLON.DirectionalLight("dir01", new BABYLON.Vector3(-1, -2, -1), scene);
light.position = new BABYLON.Vector3(20, 40, 20);
var ground01 = BABYLON.Mesh.CreateGround("Spotlight Hard Shadows", 24, 60, 1, scene, false);
var groundMaterial = new BABYLON.StandardMaterial("ground", scene);
groundMaterial.diffuseTexture = new BABYLON.Texture("images/gr1.jpg", scene);
groundMaterial.specularColor = new BABYLON.Color3(0, 0, 0);
groundMaterial.emissiveColor = new BABYLON.Color3(0.2, 0.2, 0.2);
ground01.material = groundMaterial;
ground01.receiveShadows = true;
ground01.position.x = -5;
var box = BABYLON.Mesh.CreateBox("box", 3.0, scene);
box.position.x = -5;
box.position.y = 5;
var shadowGenerator00 = new BABYLON.ShadowGenerator(512, light);
shadowGenerator00.getShadowMap().renderList.push(box);
//shadowGenerator00.usePoissonSampling = true;
//shadowGenerator00.useExponentialShadowMap = true;
shadowGenerator00.useBlurExponentialShadowMap = true;
shadowGenerator00.bias = 0.01;
scene.registerBeforeRender(function() {
box.rotation.x += 0.01;
box.rotation.x += 0.01;
});
return scene;
};
var scene = createScene();
engine.runRenderLoop(function() {
scene.render();
});
</script>
</body>
</html>
산출
위의 코드 줄은 다음 출력을 생성합니다.
설명
그림자를 만들려면 shadowgenerator를 만들어야합니다. 아래에 표시된 예를 고려하십시오.
var shadowGenerator00 = new BABYLON.ShadowGenerator(512, light);
그림자가 필요한 메시를 정의하려면 위의 생성기에 동일한 것을 추가해야합니다.
shadowGenerator00.getShadowMap().renderList.push(box);
이제 우리는 그 위에 땅과 상자를 만들었습니다. 상자의 그림자가 땅에 떨어지길 원합니다. 그러기 위해서는지면이 다음과 같이 그림자를 받도록 표시되어 있는지 확인해야합니다.
ground01.receiveShadows = true;
다음과 같은 그림자에 사용할 수있는 필터가 있습니다.
shadowGenerator.usePoissonSampling = true; - Called Poisson sampling
shadowGenerator.useExponentialShadowMap = true; - Exponential Shadow Map
shadowGenerator.useBlurExponentialShadowMap= true; - Blur Exponential Shadow Map
데모에서는 shadowGenerator00.useBlurExponentialShadowMap = true; 다른 것을 시도하고 출력이 어떻게 보이는지 볼 수 있습니다.
여기에서는 gr1.jpg라는 이미지를 사용했습니다. 이미지는 images / 폴더에 로컬로 저장됩니다. 원하는 이미지를 다운로드하여 데모 링크에서 사용할 수 있습니다.
BabylonJS – 메시의 고급 텍스처
이 섹션에서는 메시의 고급 텍스처에 대해 배웁니다. 다른 텍스처는 아래에 나와 있습니다.
큐브 텍스처
미러 및 범프 텍스처
비디오 텍스처
미러, 범프, 비디오 및 굴절과 같은 복잡한 텍스처를 메시에 적용 해 보겠습니다.
Sr. 아니. | 메시 및 설명 |
---|---|
1 | MeshHightlight 레이어 하이라이트 레이어는 장면에서 메시를 강조하는 데 사용됩니다. 색상을 지정할 수 있으며 색상은 메쉬의 테두리에 적용됩니다. 강조하려는 게임의 경우 메쉬 강조 표시 레이어를 동일하게 사용할 수 있습니다. |
2 | 메시 모프 모핑은 전환을 통해 개체의 모양을 다른 개체로 변경합니다. 모양에 대한 업데이트 가능한 매개 변수를 보았습니다. 그렇지 않으면 매개 변수가 false로 설정됩니다. 모핑의 경우 true로 설정되고 메시가 업데이트되어 모양이 변경됩니다. |
삼 | 메시 작업 작업은 메시에 상호 작용을 추가하는 데 사용됩니다. 메시를 클릭하거나 메시가 교차하거나 충돌 할 때 이벤트가 활성화됩니다. |
4 | 메시 자산 관리자 assestsmanager 클래스를 사용하면 장면에 메시, 이미지 및 바이너리 파일을로드 할 수 있습니다. |
5 | 메시 가져 오기 Import Mesh를 사용하여 배울 것입니다. |
6 | 메시 모프 타겟 우리는 이미 선, 리본, 다각형 등의 모핑을 보았습니다. 이제이 데모에서 구와 상자의 모핑을 볼 것입니다. 모프 타겟을 사용하면 구의 모양이 변경됩니다 (아래 데모에서 볼 수 있음). |
7 | 메시 인스턴스 장면에서 동일한 메시를 그리려면 인스턴스를 사용하십시오. |
8 | 메시 LOD 및 인스턴스 LOD는 거리의 선을 나타냅니다. 이 기능을 사용하면 뷰어의 거리에 따라 메시를 지정할 수 있습니다. 뷰어에서 오브젝트까지의 거리가 멀어짐에 따라 메시의 세부 수준이 LOD를 사용하여 명확하게 표시됩니다. |
9 | 메시 체적 측정 LightScattering 이 프로세스는 아래 주어진 출력에 표시된대로 빛을 산란시킵니다. 브라우저에서 동일하게 테스트하면 빛이 메시를 통해 어떻게 산란되는지 확인할 수 있습니다. |
10 | 메쉬 가장자리 EdgesRendering은 위의 출력과 같이 메시 주위에 egdes를 그리는 데 사용됩니다. |
11 | 메시 블렌드 모드 재질의 알파 모드를 수정하여 블렌드 모드를 만들 수 있습니다. |
12 | 메쉬 솔리드 입자 SolidParticle System은 메시에서 업데이트됩니다. 메쉬에서 본 모든 속성은 솔리드 입자에 사용할 수 있습니다. |
13 | 메시면 데이터 패싯 데이터는 많은 메모리를 차지하며이 기능은 기본적으로 활성화되어 있지 않습니다. 이를 활성화하려면 필요에 따라 메시를 생성하고 패싯 데이터를 업데이트해야합니다. |