I created a simple mesh in Blender, which consist only from one textured plane.
Blender screenshot
I import it in three.js with this code:
var texture2 = new THREE.TextureLoader().load('models/TexturesCom_Branches0030_1_S.png');
loader.load("models/plant.json", function (geometry, materials) {
materials.forEach(function (material) {
material.alphaTest = 0.5;
});
mesh = new THREE.Mesh( geometry, materials );
mesh.customDepthMaterial = new THREE.MeshDepthMaterial( {
side: THREE.DoubleSide,
depthPacking: THREE.RGBADepthPacking,
map: texture2,
alphaTest: 0.5
} );
mesh.castShadow = true;
mesh.receiveShadow = true;
scene.add(mesh);
});
That's how mesh looks in three.js: #1
#2
As you can see, object casts shadow not only on the ground, but on itself.
I can turn receiveShadow off, but this is not a solution for me. This problem does not disappear, if I create THREE.PlaneGeometry manually.
Related
I'm trying to make a plane in three.js that one side is a texture and the other side is a color. I tried:
var material = new THREE.MeshBasicMaterial({color: 0xff0000, side: THREE.FrontSide, map: texture});
var geometry = new THREE.PlaneGeometry(width, height);
plane = new THREE.Mesh(geometry, material);
However this makes a plane that only one side has the texture and the other side is completely transparent. If I go:
var material = new THREE.MeshBasicMaterial({color: 0xff0000});
Then both sides have the color. Is there a way to make it so one side has a texture and the other side has the color?
Here is one patten you can follow if you want a different material on the front and back of a mesh:
var group = new THREE.Group();
scene.add( group );
group.add( new THREE.Mesh( geometry, new THREE.MeshBasicMaterial( { map: texture } ) ) );
group.add( new THREE.Mesh( geometry, new THREE.MeshBasicMaterial( { color: 0xff0000, side: THREE.BackSide } ) ) );
Another approach is to write your own custom ShaderMaterial, but the above is the easiest if you are just getting started with three.js
three.js r.104
I wonder if a textured geometry can take lighting in three.js. In my scene, all materials get great lighting with spotLight and directionalLight except for materials with texture assignment like this:
var geometry = new THREE.OctahedronGeometry(1, 0)
var orange = new THREE.TextureLoader().load( 'img/orange.jpg' );
orange.wrapS = THREE.RepeatWrapping;
orange.wrapT = THREE.RepeatWrapping;
orange.repeat.set( 4, 2);
var material = new THREE.MeshBasicMaterial({
map:orange, side:THREE.DoubleSide
});
var oct0 = new THREE.Mesh( geometry, material );
oct0.castShadow = true; //default is false
oct0.receiveShadow = false; //default
scene.add( oct0 );
oct0.position.x = 0;
oct0.position.y = 5;
oct0.position.z = 0;
I am using Chrome. Safari and three.js r89. Thanks for any advice!
MeshBasicMaterial does not respond to lights.
There are other built-in materials that do. For example, MeshLambertMaterial, MeshPhongMaterial, MeshStandardMaterial.
three.js r.89
I have a tree model, that consists from only one mesh and has two materials: bark and branch. I export this mesh from Blender to .json and than add it on the scene:
var texture2 = new THREE.TextureLoader().load('models/branch1.png');
var loader = new THREE.JSONLoader();
loader.load("models/treeTest.json", function (geometry, materials) {
materials.forEach(function (material) {
material.alphaTest = 0.5;
});
mesh = new THREE.Mesh( geometry, materials );
mesh.customDepthMaterial = new THREE.MeshDepthMaterial( {
depthPacking: THREE.RGBADepthPacking,
map: texture2,
alphaTest: 0.5
} );
mesh.castShadow = true;
mesh.receiveShadow = true;
scene.add(mesh);
});
Result:
As you can see branches and bark use the same customDepthMaterial and because of that they have same shadows. I need to give customDepthMaterial only to branches, trunk must stay not transparent. I have tried to add customDepthMaterial on material with this:
materials.forEach(function (material) {
material.customDepthMaterial = new THREE.MeshDepthMaterial( {
depthPacking: THREE.RGBADepthPacking,
map: texture2,
alphaTest: 0.5
} );
});
but this code doesnt work (no errors in console, shadows just doesnt have transparency).
I know, that I can split my mesh into two parts (branches and trunk) and than use ObjectLoader, but I need the better solution.
My mesh has a baked shadow texture.
Unfortunately I got a weird result If I move the camera to a steeper viewangle.
What can I do to prevent this ?
loader.load( "mesh.js", function(geometry){
var mesh = new THREE.Mesh( geometry, new THREE.MeshPhongMaterial( {
map: THREE.ImageUtils.loadTexture( "texture.png" ),
}));
scene.add(mesh);
});
Look at the example: http://threejs.org/examples/#webgl_materials_texture_anisotropy
Use:
var maxAnisotropy = renderer.getMaxAnisotropy();
texture.anisotropy = maxAnisotropy;
If you would like to learn more, you can look up Anisotropic Filtering.
I'm trying to draw a wireframe mesh and a textured mesh in threeJS but when I have both added to my scene the textured mesh doesn't display. Code below:
I'm having trouble creating two meshes that share the same geometry where one of the materials is wireframe and the other is a texture. If one of the materials is wireframe and the other is just a color fill it works fine- but as soon as I make the second material a texture it stops working.
If I comment out scene.add( wireMesh ); then the textured mesh shows up.
var wireMat = new THREE.MeshBasicMaterial( { color:0x00FFFF, wireframe: true, transparent: true, overdraw:true } );
var wireMesh = new THREE.Mesh(geometry, wireMat);
scene.add( wireMesh );
var texture = texture = THREE.ImageUtils.loadTexture( 'textures/world.jpg' );
var imageMat = new THREE.MeshBasicMaterial( {color:0xffffff, map: texture } );
var fillMesh = new THREE.Mesh(geometry, imageMat);
scene.add( fillMesh );
Under SceneUtils there is a createMultiMaterialObject(geometry, materials). It essentially creates multiple meshes that all share the same geometry all in a group.
Example:
var mesh = THREE.SceneUtils.createMultiMaterialObject( geometry, [
new THREE.MeshLambertMaterial( { color: 0xffffff} ),
new THREE.MeshBasicMaterial( { color: 0x222222, wireframe: true} )
]);
THREE.SceneUtils source code
Unfortunately it is not possible to share geometry between an object using wireframe and another one not using it. You'd need to clone that geometry. Which reminds me that we haven't done .clone() for Geometry yet.