Javascript 如何使顶点和片段着色器在three.js中工作
我已经开始阅读一本名为《WebGL:Up and Running》的书,该书使用我首选的THREE.js解决方案在浏览器中渲染3D对象。我试图模仿书中他引入着色器来生成动态、明亮的太阳的部分,但当我尝试时得到的只是一个黑色球体。使着色器更简单(如Lampert着色器)效果很好,因此它似乎不是照明-只是着色器的实现方式 那么我做错了什么?设置场景的javascript代码是Javascript 如何使顶点和片段着色器在three.js中工作,javascript,three.js,webgl,Javascript,Three.js,Webgl,我已经开始阅读一本名为《WebGL:Up and Running》的书,该书使用我首选的THREE.js解决方案在浏览器中渲染3D对象。我试图模仿书中他引入着色器来生成动态、明亮的太阳的部分,但当我尝试时得到的只是一个黑色球体。使着色器更简单(如Lampert着色器)效果很好,因此它似乎不是照明-只是着色器的实现方式 那么我做错了什么?设置场景的javascript代码是 var renderer, scene, camera, sunMesh, clock, uniforms; $(func
var renderer, scene, camera, sunMesh, clock, uniforms;
$(function(){
//set scene size
var WIDTH = 1200,
HEIGHT = 800;
//set some camera attributes
var VIEW_ANGLE = 45,
ASPECT = WIDTH / HEIGHT,
NEAR = 0.1,
FAR = 10000;
// get the DOM element to attach to
// - assume we've got jQuery to hand
var $container = $('#container');
// create a WebGL renderer, camera
// and a scene
renderer = new THREE.WebGLRenderer();
camera = new THREE.PerspectiveCamera( VIEW_ANGLE,
ASPECT,
NEAR,
FAR );
scene = new THREE.Scene();
// the camera starts at 0,0,0 so pull it back
camera.position.z = 300;
// start the renderer
renderer.setSize(WIDTH, HEIGHT);
// attach the render-supplied DOM element
$container.append(renderer.domElement);
// Create a group to hold our sun mesh and light
var sunGroup = new THREE.Object3D();
var SUNMAP = "./images/lavatile.jpg";
var NOISEMAP = "./images/cloud.png";
uniforms = {
time: { type: "f", value: 1.0 },
texture1: { type: "t", value: 0, texture: THREE.ImageUtils.loadTexture( NOISEMAP ) },
texture2: { type: "t", value: 1, texture: THREE.ImageUtils.loadTexture( SUNMAP ) }
};
uniforms.texture1.texture.wrapS = uniforms.texture1.texture.wrapT = THREE.Repeat;
uniforms.texture2.texture.wrapS = uniforms.texture2.texture.wrapT = THREE.Repeat;
var material = new THREE.ShaderMaterial( {
uniforms: uniforms,
vertexShader: document.getElementById( 'vertexShader' ).textContent,
fragmentShader: document.getElementById( 'fragmentShader' ).textContent
} );
//USING THIS MATERIAL WORKS, SO ITS DEFINITELY THE SHADER!
//var material = new THREE.MeshLambertMaterial(
//{
// color: 0x5B92E5
//});
// Create our sun mesh
var geometry = new THREE.SphereGeometry(50, 64, 64);
sunMesh = new THREE.Mesh( geometry, material );
// Tuck away the uniforms so that we can animate them over time
// Set up a clock to drive the animation
clock = new THREE.Clock();
// Create a point light to show off our solar system
var light = new THREE.PointLight( 0xffffff );
light.position.set(0,0,100);
sunGroup.add(sunMesh);
sunGroup.add(light);
scene.add(sunGroup);
// and the camera
scene.add(camera);
renderer.render(scene, camera);
// setup an interval to loop the game loop
setInterval(gameloop, 50);
});
function gameloop() {
var delta = clock.getDelta();
uniforms.time.value += delta;
renderer.render(scene, camera);
}
我将保存完整的HTML(在中列出),但其中包含我的着色器,这是我从WebGL书籍的源代码中提取的。这些可能是错误的,但我怀疑这是我使用着色器的方式。据我所知,我应该看到一个太阳,其纹理根据噪波遮挡贴图发生变化,在顶点位置进行一些移动以使太阳脉冲。正如我所说,我可以看到一个球体,但它没有发光,是黑色的
我哪里出错了?真遗憾。这本书似乎已经过时了 Three.js是alpha版本,并且变化很快从三个.js示例中学习。它们总是最新的 查看以获取升级到当前版本的帮助 代码中的一些明显错误:
texture1: { type: "t", value: 0, texture: THREE.ImageUtils.loadTexture( NOISEMAP ) },
应该是
texture1: { type: "t", value: THREE.ImageUtils.loadTexture( NOISEMAP ) },
THREE.Repeat
应该是THREE.RepeatWrapping
,而uniforms.texture1.texture
应该是uniforms.texture1.value
抱歉,您可能有其他问题,但我只能在three.js的当前版本中帮助您
three.js r.54谢谢你,我也很害怕。将在API中搜索这些,但是ShaderMaterial上的文档很难/不可能找到。我最近在和上发布了一些简单的着色器示例,它不能替代文档,但它可能足以让您开始。祝你好运