为什么不透明度会因相机角度而异?
Why is the opacity different depending on the camera angle?
第一次加载场景时,左右平移时,左边的条是半透明的,右边的是不透明的。如果你向右移动(键 d)最右边的条,所有的条都会变得透明。这是照明问题还是我设置光源的方式?
// default alpha for bars
var alpha = 0.6
// fake data
var data = [19, 80, 30, 15, 55, 35, 40,
45, 50, 70, 109, 35, 78,
87, 76, 22, 2, 33, 44, 59, 200
]
var animals = ['Bobcat', 'Dog', 'Cat', 'Boar', 'Cheetah', 'Chimp', 'Dragon',
'Elephant', 'Human', 'Elf', 'Giant', 'Batman', 'Donkey',
'Henry', 'Face', 'Funny', 'Kitty', 'Doggy', 'Joker', 'Alf', 'Earth'
]
// we scale the height of our bars using d3's linear scale
var hscale = d3.scale.linear()
.domain([0, d3.max(data)])
.range([0, 3])
// we select the scene object just like an svg
var scene = d3.select("a-scene")
// we use d3's enter/update/exit pattern to draw and bind our dom elements
var bars = scene.selectAll("a-box.bar").data(data)
bars.enter().append("a-box").classed("bar", true)
$(".bar").append("<a-text> </a-text>");
// we set attributes on our cubes to determine how they are rendered
bars.attr({
position: function(d, i) {
var x = i * .75
var y = hscale(d) / 2;
var z = 1
return x + " " + y + " " + z
},
width: function(d) {
return 0.5
},
depth: function(d) {
return 0.9
},
height: function(d) {
return hscale(d)
},
opacity: alpha,
color: 'blue'
})
.on("click", function(d, i) {
console.log("click", i, d)
})
.on("mouseenter", function(d, i) {
// this event gets fired continuously as long as the cursor
// is over the element. we only want trigger our animation the first time
if (this.hovering) return;
console.log("hover", i, d)
this.hovering = true;
d3.select(this).transition().duration(10)
.attr({
metalness: 0.8,
opacity: .9
})
d3.select(this).select("a-text")
.attr({
'color': 'hsla(240, 100%, 25%, 0.6)',
'align': 'center',
'position': '0 ' + (hscale(d) / 2 + .5) + ' 0',
'scale': '1 1 1',
'value': animals[i] + ', ' + d
})
})
.on("mouseleave", function(d, i) {
console.log("leave", i, d)
this.hovering = false;
d3.select(this).transition().duration(500)
.attr({
metalness: 0,
opacity: alpha
})
d3.select(this).select("a-text")
.attr({
'color': 'blue',
'align': 'center',
'position': '0 ' + (hscale(d) / 2 + .5) + ' 0',
'scale': '.01 .01 .01',
'value': d
})
})
<head>
<script src="https://aframe.io/releases/0.5.0/aframe.min.js"></script>
<script src="https://code.jquery.com/jquery-3.1.1.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/3.5.5/d3.min.js"></script>
</head>
<body>
<a-scene>
<a-entity position="8 2 8" rotation="0 0 0">
<a-entity camera look-controls wasd-controls>
<a-entity cursor="fuse: true; fuseTimeout: 500" position="0 0 -2" geometry="primitive: ring; radiusInner: 0.02; radiusOuter: 0.027" material="color: black; shader: flat" </a-entity>
</a-entity>
</a-entity>
<a-entity light="type: point; color: 'white'; intensity: 0.5" position="20 40 20"></a-entity>
<a-entity light="type: point; color: 'white'; intensity: 0.5" position="-20 40 20"></a-entity>
<a-sky color="#c8f8e0"></a-sky>
</a-scene>
<body>
来自Three.js / WebGL - transparent planes hiding other planes behind them
Transparent surfaces don't play well with the z-buffer, and as such must be manually sorted and rendered back-to-front. three.js is attempting to do this for you (which is why the problem goes away depending on the angle of the camera) but cannot robustly handle the case of intersecting geometry like you're showing.
我通过更改 material 的 alphaTest
值或 depthWrite
值使其工作:
el.components.material.material.alphaTest = 0.5;
el.components.material.material.depthWrite = false;
el.components.material.material.needsUpdate = true;
第一次加载场景时,左右平移时,左边的条是半透明的,右边的是不透明的。如果你向右移动(键 d)最右边的条,所有的条都会变得透明。这是照明问题还是我设置光源的方式?
// default alpha for bars
var alpha = 0.6
// fake data
var data = [19, 80, 30, 15, 55, 35, 40,
45, 50, 70, 109, 35, 78,
87, 76, 22, 2, 33, 44, 59, 200
]
var animals = ['Bobcat', 'Dog', 'Cat', 'Boar', 'Cheetah', 'Chimp', 'Dragon',
'Elephant', 'Human', 'Elf', 'Giant', 'Batman', 'Donkey',
'Henry', 'Face', 'Funny', 'Kitty', 'Doggy', 'Joker', 'Alf', 'Earth'
]
// we scale the height of our bars using d3's linear scale
var hscale = d3.scale.linear()
.domain([0, d3.max(data)])
.range([0, 3])
// we select the scene object just like an svg
var scene = d3.select("a-scene")
// we use d3's enter/update/exit pattern to draw and bind our dom elements
var bars = scene.selectAll("a-box.bar").data(data)
bars.enter().append("a-box").classed("bar", true)
$(".bar").append("<a-text> </a-text>");
// we set attributes on our cubes to determine how they are rendered
bars.attr({
position: function(d, i) {
var x = i * .75
var y = hscale(d) / 2;
var z = 1
return x + " " + y + " " + z
},
width: function(d) {
return 0.5
},
depth: function(d) {
return 0.9
},
height: function(d) {
return hscale(d)
},
opacity: alpha,
color: 'blue'
})
.on("click", function(d, i) {
console.log("click", i, d)
})
.on("mouseenter", function(d, i) {
// this event gets fired continuously as long as the cursor
// is over the element. we only want trigger our animation the first time
if (this.hovering) return;
console.log("hover", i, d)
this.hovering = true;
d3.select(this).transition().duration(10)
.attr({
metalness: 0.8,
opacity: .9
})
d3.select(this).select("a-text")
.attr({
'color': 'hsla(240, 100%, 25%, 0.6)',
'align': 'center',
'position': '0 ' + (hscale(d) / 2 + .5) + ' 0',
'scale': '1 1 1',
'value': animals[i] + ', ' + d
})
})
.on("mouseleave", function(d, i) {
console.log("leave", i, d)
this.hovering = false;
d3.select(this).transition().duration(500)
.attr({
metalness: 0,
opacity: alpha
})
d3.select(this).select("a-text")
.attr({
'color': 'blue',
'align': 'center',
'position': '0 ' + (hscale(d) / 2 + .5) + ' 0',
'scale': '.01 .01 .01',
'value': d
})
})
<head>
<script src="https://aframe.io/releases/0.5.0/aframe.min.js"></script>
<script src="https://code.jquery.com/jquery-3.1.1.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/3.5.5/d3.min.js"></script>
</head>
<body>
<a-scene>
<a-entity position="8 2 8" rotation="0 0 0">
<a-entity camera look-controls wasd-controls>
<a-entity cursor="fuse: true; fuseTimeout: 500" position="0 0 -2" geometry="primitive: ring; radiusInner: 0.02; radiusOuter: 0.027" material="color: black; shader: flat" </a-entity>
</a-entity>
</a-entity>
<a-entity light="type: point; color: 'white'; intensity: 0.5" position="20 40 20"></a-entity>
<a-entity light="type: point; color: 'white'; intensity: 0.5" position="-20 40 20"></a-entity>
<a-sky color="#c8f8e0"></a-sky>
</a-scene>
<body>
来自Three.js / WebGL - transparent planes hiding other planes behind them
Transparent surfaces don't play well with the z-buffer, and as such must be manually sorted and rendered back-to-front. three.js is attempting to do this for you (which is why the problem goes away depending on the angle of the camera) but cannot robustly handle the case of intersecting geometry like you're showing.
我通过更改 material 的 alphaTest
值或 depthWrite
值使其工作:
el.components.material.material.alphaTest = 0.5;
el.components.material.material.depthWrite = false;
el.components.material.material.needsUpdate = true;