mirror of
https://github.com/wahyd4/three.js.git
synced 2026-08-13 15:05:56 +10:00
Changed normal map shader to multiply specular component with diffuse weighting as specular highlights were appearing in the dark parts. Changed camera look speed in minecraft and terrain demos, they were too fast - I guess as everything got faster with antialiasing off. Reenabled antialiasing in few demos where it was too ugly without (basically anything with lines and without postprocessing). Fixed again spurious invisible characters in empaempa's code (which are breaking everything and are hard to hunt as they look like spaces).
275 lines
6.9 KiB
HTML
275 lines
6.9 KiB
HTML
<!DOCTYPE HTML>
|
|
<html lang="en">
|
|
<head>
|
|
<title>three.js webgl - interactive - voxel painter</title>
|
|
<meta charset="utf-8">
|
|
<style type="text/css">
|
|
body {
|
|
font-family: Monospace;
|
|
background-color: #f0f0f0;
|
|
margin: 0px;
|
|
overflow: hidden;
|
|
}
|
|
|
|
#oldie { background-color: #ddd !important }
|
|
</style>
|
|
</head>
|
|
<body>
|
|
|
|
<script type="text/javascript" src="../build/Three.js"></script>
|
|
|
|
<script type="text/javascript" src="js/Detector.js"></script>
|
|
<script type="text/javascript" src="js/RequestAnimationFrame.js"></script>
|
|
<script type="text/javascript" src="js/Stats.js"></script>
|
|
|
|
<script type="text/javascript">
|
|
|
|
if ( ! Detector.webgl ) Detector.addGetWebGLMessage();
|
|
|
|
var container, stats;
|
|
var camera, scene, renderer;
|
|
var projector, plane, cube;
|
|
var mouse2D, mouse3D, ray,
|
|
rollOveredFace, isShiftDown = false,
|
|
theta = 45, isCtrlDown = false;
|
|
|
|
var rollOverMesh, rollOverMaterial, voxelPosition = new THREE.Vector3(), tmpVec = new THREE.Vector3();
|
|
var cubeGeo, cubeMaterial;
|
|
var i, intersector;
|
|
|
|
init();
|
|
animate();
|
|
|
|
function init() {
|
|
|
|
container = document.createElement( 'div' );
|
|
document.body.appendChild( container );
|
|
|
|
var info = document.createElement( 'div' );
|
|
info.style.position = 'absolute';
|
|
info.style.top = '10px';
|
|
info.style.width = '100%';
|
|
info.style.textAlign = 'center';
|
|
info.innerHTML = '<a href="http://github.com/mrdoob/three.js" target="_blank">three.js</a> - voxel painter - webgl<br /><strong>click</strong>: add voxel, <strong>control + click</strong>: remove voxel, <strong>shift + click</strong>: rotate, <a href="javascript:save();return false;">save .png</a>';
|
|
container.appendChild( info );
|
|
|
|
camera = new THREE.Camera( 40, window.innerWidth / window.innerHeight, 1, 10000 );
|
|
camera.position.y = 800;
|
|
camera.target.position.y = 200;
|
|
|
|
scene = new THREE.Scene();
|
|
|
|
// roll-over helpers
|
|
|
|
rollOverGeo = new THREE.Cube( 50, 50, 50 );
|
|
rollOverMaterial = new THREE.MeshBasicMaterial( { color: 0xff0000, opacity: 0.5, transparent: true } );
|
|
rollOverMesh = new THREE.Mesh( rollOverGeo, rollOverMaterial );
|
|
scene.addObject( rollOverMesh );
|
|
|
|
|
|
// cubes
|
|
|
|
cubeGeo = new THREE.Cube( 50, 50, 50 );
|
|
cubeMaterial = new THREE.MeshLambertMaterial( { color: 0x00ff80, shading: THREE.FlatShading, map: THREE.ImageUtils.loadTexture( "textures/square-outline-textured.png" ) } );
|
|
cubeMaterial.color.setHSV( 0.1, 0.7, 1.0 );
|
|
// picking
|
|
|
|
projector = new THREE.Projector();
|
|
|
|
// grid
|
|
|
|
plane = new THREE.Mesh( new THREE.Plane( 1000, 1000, 20, 20 ), new THREE.MeshBasicMaterial( { color: 0x555555, wireframe: true } ) );
|
|
plane.rotation.x = - 90 * Math.PI / 180;
|
|
scene.addObject( plane );
|
|
|
|
mouse2D = new THREE.Vector3( 0, 10000, 0.5 );
|
|
ray = new THREE.Ray( camera.position, null );
|
|
|
|
// Lights
|
|
|
|
var ambientLight = new THREE.AmbientLight( 0x606060 );
|
|
scene.addLight( ambientLight );
|
|
|
|
var directionalLight = new THREE.DirectionalLight( 0xffffff );
|
|
directionalLight.position.x = Math.random() - 0.5;
|
|
directionalLight.position.y = Math.random() - 0.5;
|
|
directionalLight.position.z = Math.random() - 0.5;
|
|
directionalLight.position.normalize();
|
|
scene.addLight( directionalLight );
|
|
|
|
var directionalLight = new THREE.DirectionalLight( 0x808080 );
|
|
directionalLight.position.x = Math.random() - 0.5;
|
|
directionalLight.position.y = Math.random() - 0.5;
|
|
directionalLight.position.z = Math.random() - 0.5;
|
|
directionalLight.position.normalize();
|
|
scene.addLight( directionalLight );
|
|
|
|
renderer = new THREE.WebGLRenderer( { antialias: true } );
|
|
renderer.setSize( window.innerWidth, window.innerHeight );
|
|
|
|
container.appendChild( renderer.domElement );
|
|
|
|
stats = new Stats();
|
|
stats.domElement.style.position = 'absolute';
|
|
stats.domElement.style.top = '0px';
|
|
container.appendChild( stats.domElement );
|
|
|
|
document.addEventListener( 'mousemove', onDocumentMouseMove, false );
|
|
document.addEventListener( 'mousedown', onDocumentMouseDown, false );
|
|
document.addEventListener( 'keydown', onDocumentKeyDown, false );
|
|
document.addEventListener( 'keyup', onDocumentKeyUp, false );
|
|
|
|
}
|
|
|
|
function getRealIntersector( intersects ) {
|
|
|
|
for( i = 0; i < intersects.length; i++ ) {
|
|
|
|
intersector = intersects[ i ];
|
|
|
|
if ( intersector.object != rollOverMesh ) {
|
|
|
|
return intersector;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return null;
|
|
|
|
}
|
|
|
|
function setVoxelPosition( intersector ) {
|
|
|
|
tmpVec.copy( intersector.face.normal );
|
|
|
|
voxelPosition.add( intersector.point, intersector.object.matrixRotationWorld.multiplyVector3( tmpVec ) );
|
|
|
|
voxelPosition.x = Math.floor( voxelPosition.x / 50 ) * 50 + 25;
|
|
voxelPosition.y = Math.floor( voxelPosition.y / 50 ) * 50 + 25;
|
|
voxelPosition.z = Math.floor( voxelPosition.z / 50 ) * 50 + 25;
|
|
|
|
}
|
|
|
|
function onDocumentMouseMove( event ) {
|
|
|
|
event.preventDefault();
|
|
|
|
mouse2D.x = ( event.clientX / window.innerWidth ) * 2 - 1;
|
|
mouse2D.y = - ( event.clientY / window.innerHeight ) * 2 + 1;
|
|
|
|
}
|
|
|
|
function onDocumentMouseDown( event ) {
|
|
|
|
event.preventDefault();
|
|
|
|
var intersects = ray.intersectScene( scene );
|
|
|
|
if ( intersects.length > 0 ) {
|
|
|
|
intersector = getRealIntersector( intersects );
|
|
|
|
// delete cube
|
|
|
|
if ( isCtrlDown ) {
|
|
|
|
if ( intersector.object != plane ) {
|
|
|
|
scene.removeObject( intersector.object );
|
|
|
|
}
|
|
|
|
// create cube
|
|
|
|
} else {
|
|
|
|
intersector = getRealIntersector( intersects );
|
|
setVoxelPosition( intersector );
|
|
|
|
var voxel = new THREE.Mesh( cubeGeo, cubeMaterial );
|
|
voxel.position.copy( voxelPosition );
|
|
voxel.matrixAutoUpdate = false;
|
|
voxel.updateMatrix();
|
|
scene.addObject( voxel );
|
|
|
|
}
|
|
|
|
}
|
|
}
|
|
|
|
function onDocumentKeyDown( event ) {
|
|
|
|
switch( event.keyCode ) {
|
|
|
|
case 16: isShiftDown = true; break;
|
|
case 17: isCtrlDown = true; break;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
function onDocumentKeyUp( event ) {
|
|
|
|
switch( event.keyCode ) {
|
|
|
|
case 16: isShiftDown = false; break;
|
|
case 17: isCtrlDown = false; break;
|
|
|
|
}
|
|
}
|
|
|
|
function save() {
|
|
|
|
window.open( renderer.domElement.toDataURL('image/png'), 'mywindow' );
|
|
|
|
}
|
|
|
|
//
|
|
|
|
function animate() {
|
|
|
|
requestAnimationFrame( animate );
|
|
|
|
render();
|
|
stats.update();
|
|
|
|
}
|
|
|
|
function render() {
|
|
|
|
if ( isShiftDown ) {
|
|
|
|
theta += mouse2D.x * 3;
|
|
|
|
}
|
|
|
|
mouse3D = projector.unprojectVector( mouse2D.clone(), camera );
|
|
ray.direction = mouse3D.subSelf( camera.position ).normalize();
|
|
|
|
var intersects = ray.intersectScene( scene );
|
|
|
|
if ( intersects.length > 0 ) {
|
|
|
|
intersector = getRealIntersector( intersects );
|
|
if ( intersector ) {
|
|
|
|
setVoxelPosition( intersector );
|
|
rollOverMesh.position = voxelPosition;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
camera.position.x = 1400 * Math.sin( theta * Math.PI / 360 );
|
|
camera.position.z = 1400 * Math.cos( theta * Math.PI / 360 );
|
|
|
|
renderer.render( scene, camera );
|
|
|
|
}
|
|
|
|
</script>
|
|
|
|
</body>
|
|
</html>
|