mirror of https://gitee.com/antv-l7/antv-l7
feat: lighting
This commit is contained in:
parent
a233c588f4
commit
f8269ee35b
|
@ -32,35 +32,35 @@ const scene = new L7.Scene({
|
|||
});
|
||||
window.scene = scene;
|
||||
scene.on('loaded', () => {
|
||||
$.get('https://gw.alipayobjects.com/os/rmsportal/XHMbjQwrSrajvLLvMPbK.json', data => {
|
||||
scene.PolygonLayer({
|
||||
zIndex: 0
|
||||
})
|
||||
.source(data)
|
||||
.shape('fill')
|
||||
.active({fill:'blue'})
|
||||
.color('rgb(79,174,234)')
|
||||
.render();
|
||||
});
|
||||
$.get('https://gw.alipayobjects.com/os/rmsportal/VifgwJEyBIXnDrjCwWdK.json', data => {
|
||||
scene.PolygonLayer({
|
||||
zIndex: 0
|
||||
})
|
||||
.source(data)
|
||||
.shape('fill')
|
||||
.color('rgb(156,194,116)')
|
||||
.render();
|
||||
});
|
||||
$.get('https://gw.alipayobjects.com/os/rmsportal/ZseLNWMOPGrgqQYfvtli.json', data => {
|
||||
scene.LineLayer({
|
||||
zIndex: 2
|
||||
})
|
||||
.source(data)
|
||||
.shape('line')
|
||||
.size([3,0])
|
||||
.color('rgb(79,174,234)')
|
||||
.render();
|
||||
});
|
||||
// $.get('https://gw.alipayobjects.com/os/rmsportal/XHMbjQwrSrajvLLvMPbK.json', data => {
|
||||
// scene.PolygonLayer({
|
||||
// zIndex: 0
|
||||
// })
|
||||
// .source(data)
|
||||
// .shape('fill')
|
||||
// .active({fill:'blue'})
|
||||
// .color('rgb(79,174,234)')
|
||||
// .render();
|
||||
// });
|
||||
// $.get('https://gw.alipayobjects.com/os/rmsportal/VifgwJEyBIXnDrjCwWdK.json', data => {
|
||||
// scene.PolygonLayer({
|
||||
// zIndex: 0
|
||||
// })
|
||||
// .source(data)
|
||||
// .shape('fill')
|
||||
// .color('rgb(156,194,116)')
|
||||
// .render();
|
||||
// });
|
||||
// $.get('https://gw.alipayobjects.com/os/rmsportal/ZseLNWMOPGrgqQYfvtli.json', data => {
|
||||
// scene.LineLayer({
|
||||
// zIndex: 2
|
||||
// })
|
||||
// .source(data)
|
||||
// .shape('line')
|
||||
// .size([3,0])
|
||||
// .color('rgb(79,174,234)')
|
||||
// .render();
|
||||
// });
|
||||
|
||||
$.get('https://gw.alipayobjects.com/os/rmsportal/ggFwDClGjjvpSMBIrcEx.json', data => {
|
||||
citylayer = scene.PolygonLayer({
|
||||
|
@ -69,6 +69,24 @@ scene.on('loaded', () => {
|
|||
.source(data)
|
||||
.shape('extrude')
|
||||
.active({fill:'red'})
|
||||
// .style({
|
||||
// lights: [
|
||||
// {
|
||||
// type: 'directional',
|
||||
// direction: [ 1, -10.5, 12 ],
|
||||
// ambient: [ 0.2, 0.2, 0.2 ],
|
||||
// diffuse: 'red',
|
||||
// specular: [ 0.1, 0.1, 0.1 ]
|
||||
// },
|
||||
// {
|
||||
// type: 'directional',
|
||||
// direction: [ 1, 10.5, 12 ],
|
||||
// ambient: [ 0.2, 0.2, 0.2 ],
|
||||
// diffuse: 'green',
|
||||
// specular: [ 0.1, 0.1, 0.1 ]
|
||||
// },
|
||||
// ]
|
||||
// })
|
||||
.size('floor',[10,2000])
|
||||
.color('rgba(242,246,250,0.96)')
|
||||
.render();
|
||||
|
|
|
@ -52,11 +52,13 @@ import common from './common.glsl';
|
|||
import { registerModule } from '../../util/shaderModule';
|
||||
import pick_color from './shaderChunks/pick_color.glsl';
|
||||
import decode from './shaderChunks/decode.glsl';
|
||||
import lighting from './shaderChunks/lighting.glsl';
|
||||
|
||||
export function compileBuiltinModules() {
|
||||
registerModule('point', { vs: point_vert, fs: point_frag });
|
||||
registerModule('common', { vs: common, fs: common });
|
||||
registerModule('decode', { vs: decode, fs: '' });
|
||||
registerModule('lighting', { vs: lighting, fs: '' });
|
||||
registerModule('pick_color', { vs: pick_color, fs: pick_color });
|
||||
registerModule('circle', { vs: circle_vert, fs: circle_frag });
|
||||
registerModule('polygon', { vs: polygon_vert, fs: polygon_frag });
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
precision highp float;
|
||||
uniform sampler2D u_texture;
|
||||
|
||||
uniform vec4 u_baseColor;
|
||||
uniform vec4 u_brightColor;
|
||||
uniform vec4 u_windowColor;
|
||||
|
@ -7,10 +7,12 @@ uniform float u_zoom;
|
|||
uniform float u_time;
|
||||
uniform float u_near;
|
||||
uniform float u_far;
|
||||
|
||||
#ifdef ANIMATE
|
||||
varying vec2 v_texCoord;
|
||||
varying vec4 v_color;
|
||||
varying float v_lightWeight;
|
||||
varying float v_size;
|
||||
#endif
|
||||
|
||||
varying vec4 v_color;
|
||||
varying vec4 worldId;
|
||||
|
||||
vec3 getWindowColor(float n, float hot, vec3 brightColor, vec3 darkColor) {
|
||||
|
@ -41,12 +43,6 @@ float sdRect(vec2 p, vec2 sz) {
|
|||
float inside = min(max(d.x, d.y), 0.);
|
||||
return outside + inside;
|
||||
}
|
||||
float circle(in vec2 _st, in float _radius){
|
||||
vec2 dist = _st-vec2(0.5);
|
||||
return 1.-smoothstep(_radius-(_radius*0.01),
|
||||
_radius+(_radius*0.01),
|
||||
dot(dist,dist)*4.0);
|
||||
}
|
||||
|
||||
void main() {
|
||||
if(v_color.w == 0.0) {
|
||||
|
@ -104,19 +100,13 @@ void main() {
|
|||
// if(head ==1.0) { // 顶部亮线
|
||||
// color = brightColor;
|
||||
// }
|
||||
color = color * v_lightWeight;
|
||||
color = v_color.rgb;
|
||||
|
||||
vec3 foggedColor = fog(color,fogColor,depth);
|
||||
|
||||
gl_FragColor = vec4(foggedColor,1.0);
|
||||
}
|
||||
#else
|
||||
// #ifdef SHAPE
|
||||
// vec2 st = gl_FragCoord.xy / v_size ;
|
||||
// vec3 color = vec3(circle(st,0.5));
|
||||
// gl_FragColor = vec4(color, 1.0 );
|
||||
// return;
|
||||
// #endif
|
||||
gl_FragColor = vec4(v_color.xyz , v_color.w);
|
||||
#endif
|
||||
|
||||
|
|
|
@ -1,61 +1,50 @@
|
|||
precision highp float;
|
||||
#define ambientRatio 0.5
|
||||
#define diffuseRatio 0.4
|
||||
#define specularRatio 0.1
|
||||
attribute vec4 a_color;
|
||||
attribute vec2 faceUv;
|
||||
attribute vec3 a_shape;
|
||||
attribute vec3 a_size;
|
||||
uniform float u_zoom;
|
||||
uniform float u_opacity;
|
||||
varying vec2 v_texCoord;
|
||||
varying vec4 v_color;
|
||||
varying float v_lightWeight;
|
||||
varying float v_size;
|
||||
uniform float u_activeId;
|
||||
uniform vec4 u_activeColor;
|
||||
void main() {
|
||||
float scale = pow(2.0,(20.0 - u_zoom));
|
||||
mat4 matModelViewProjection = projectionMatrix * modelViewMatrix;
|
||||
worldId = id_toPickColor(pickingId);
|
||||
vec3 newposition = position;
|
||||
// newposition.x -= 128.0;
|
||||
#ifdef SHAPE
|
||||
newposition =position + a_size * scale* a_shape + vec3(0., a_size.y * scale / 4., 0.);
|
||||
#endif
|
||||
v_texCoord = faceUv;
|
||||
if(normal == vec3(0.,0.,1.)){
|
||||
v_color = a_color;
|
||||
v_color.a *= u_opacity;
|
||||
if(pickingId == u_activeId) {
|
||||
v_color = u_activeColor;
|
||||
}
|
||||
v_size = a_size.x * scale;
|
||||
gl_Position = matModelViewProjection * vec4(newposition, 1.0);
|
||||
return;
|
||||
}
|
||||
|
||||
vec3 worldPos = vec3(vec4(newposition,1.0) * modelMatrix);
|
||||
vec3 worldNormal = vec3(vec4(normal,1.0) * modelMatrix);
|
||||
// //cal light weight
|
||||
vec3 viewDir = normalize(cameraPosition - worldPos);
|
||||
//vec3 lightDir = normalize(vec3(1, -10.5, 12));
|
||||
vec3 lightDir = normalize(vec3(0.,-10.,1.));
|
||||
vec3 halfDir = normalize(viewDir+lightDir);
|
||||
// //lambert
|
||||
float lambert = dot(worldNormal, lightDir);
|
||||
//specular
|
||||
float specular = pow( max(0.0, dot(worldNormal, halfDir)), 32.0);
|
||||
//sum to light weight
|
||||
float lightWeight = ambientRatio + diffuseRatio * lambert + specularRatio * specular;
|
||||
v_texCoord = faceUv;
|
||||
v_lightWeight = lightWeight;
|
||||
|
||||
v_color =vec4(a_color.rgb*lightWeight, a_color.w);
|
||||
if(pickingId == u_activeId) {
|
||||
v_color = u_activeColor;
|
||||
}
|
||||
gl_Position = matModelViewProjection * vec4(newposition, 1.0);
|
||||
|
||||
|
||||
attribute vec4 a_color;
|
||||
|
||||
#ifdef SHAPE
|
||||
attribute vec3 a_size;
|
||||
attribute vec3 a_shape;
|
||||
#endif
|
||||
|
||||
#ifdef ANIMATE
|
||||
attribute vec2 faceUv;
|
||||
varying vec2 v_texCoord;
|
||||
#endif
|
||||
|
||||
varying vec4 v_color;
|
||||
|
||||
uniform float u_zoom;
|
||||
uniform float u_opacity : 1.0;
|
||||
uniform float u_activeId : 0;
|
||||
uniform vec4 u_activeColor : [1.0, 0.0, 0.0, 1.0];
|
||||
|
||||
#pragma include "lighting"
|
||||
|
||||
void main() {
|
||||
#ifdef ANIMATE
|
||||
v_texCoord = faceUv;
|
||||
#endif
|
||||
v_color = a_color;
|
||||
v_color.a *= u_opacity;
|
||||
|
||||
// put offset in world space & shrink with current zoom level
|
||||
float scale = pow(2.0,(20.0 - u_zoom));
|
||||
vec3 offset = vec3(0.);
|
||||
#ifdef SHAPE
|
||||
offset = vec3(a_size * scale * a_shape);
|
||||
#endif
|
||||
gl_Position = projectionMatrix * modelViewMatrix * vec4(position + offset, 1.);
|
||||
|
||||
#ifdef LIGHTING
|
||||
if (normal != vec3(0., 0., 1.)) {
|
||||
vec3 viewDir = normalize(cameraPosition - position);
|
||||
v_color.rgb *= calc_lighting(position, normal, viewDir);
|
||||
}
|
||||
#endif
|
||||
|
||||
if(pickingId == u_activeId) {
|
||||
v_color = u_activeColor;
|
||||
}
|
||||
worldId = id_toPickColor(pickingId);
|
||||
}
|
|
@ -0,0 +1,98 @@
|
|||
// Blinn-Phong model
|
||||
// apply lighting in vertex shader instead of fragment shader
|
||||
// @see https://learnopengl.com/Advanced-Lighting/Advanced-Lighting
|
||||
// TODO: support point light、spot light & sun light
|
||||
uniform float u_ambient : 1.0;
|
||||
uniform float u_diffuse : 1.0;
|
||||
uniform float u_specular : 1.0;
|
||||
uniform int u_num_of_directional_lights : 1;
|
||||
uniform int u_num_of_spot_lights : 0;
|
||||
|
||||
#define SHININESS 32.0
|
||||
#define MAX_NUM_OF_DIRECTIONAL_LIGHTS 3
|
||||
#define MAX_NUM_OF_SPOT_LIGHTS 3
|
||||
|
||||
struct DirectionalLight {
|
||||
vec3 direction;
|
||||
vec3 ambient;
|
||||
vec3 diffuse;
|
||||
vec3 specular;
|
||||
};
|
||||
|
||||
struct SpotLight {
|
||||
vec3 position;
|
||||
vec3 direction;
|
||||
vec3 ambient;
|
||||
vec3 diffuse;
|
||||
vec3 specular;
|
||||
float constant;
|
||||
float linear;
|
||||
float quadratic;
|
||||
float angle;
|
||||
float blur;
|
||||
float exponent;
|
||||
};
|
||||
|
||||
uniform DirectionalLight u_directional_lights[MAX_NUM_OF_DIRECTIONAL_LIGHTS];
|
||||
uniform SpotLight u_spot_lights[MAX_NUM_OF_SPOT_LIGHTS];
|
||||
|
||||
vec3 calc_directional_light(DirectionalLight light, vec3 normal, vec3 viewDir) {
|
||||
vec3 lightDir = normalize(-light.direction);
|
||||
// diffuse shading
|
||||
float diff = max(dot(normal, lightDir), 0.0);
|
||||
// Blinn-Phong specular shading
|
||||
vec3 halfwayDir = normalize(lightDir + viewDir);
|
||||
float spec = pow(max(dot(normal, halfwayDir), 0.0), SHININESS);
|
||||
|
||||
vec3 ambient = light.ambient * u_ambient;
|
||||
vec3 diffuse = light.diffuse * diff * u_diffuse;
|
||||
vec3 specular = light.specular * spec * u_specular;
|
||||
|
||||
return ambient + diffuse + specular;
|
||||
}
|
||||
|
||||
// vec3 calc_spot_light(SpotLight light, vec3 normal, vec3 fragPos, vec3 viewDir) {
|
||||
// vec3 lightDir = normalize(light.position - fragPos);
|
||||
// // diffuse shading
|
||||
// float diff = max(dot(normal, lightDir), 0.0);
|
||||
// // specular shading
|
||||
// vec3 reflectDir = reflect(-lightDir, normal);
|
||||
// float spec = pow(max(dot(viewDir, reflectDir), 0.0), SHININESS);
|
||||
// // attenuation
|
||||
// float distance = length(light.position - fragPos);
|
||||
// float attenuation = 1.0 / (light.constant + light.linear * distance +
|
||||
// light.quadratic * (distance * distance));
|
||||
|
||||
// vec3 ambient = light.ambient * u_ambient;
|
||||
// vec3 diffuse = light.diffuse * diff * u_diffuse;
|
||||
// vec3 specular = light.specular * spec * u_specular;
|
||||
|
||||
// float spotEffect = dot(normalize(light.direction), -lightDir);
|
||||
// float spotCosCutoff = cos(light.angle / 180.0 * PI);
|
||||
// float spotCosOuterCutoff = cos((light.angle + light.blur) / 180.0 * PI);
|
||||
// float spotCosInnerCutoff = cos((light.angle - light.blur) / 180.0 * PI);
|
||||
// if (spotEffect > spotCosCutoff) {
|
||||
// spotEffect = pow(smoothstep(spotCosOuterCutoff, spotCosInnerCutoff, spotEffect), light.exponent);
|
||||
// } else {
|
||||
// spotEffect = 0.0;
|
||||
// }
|
||||
|
||||
// return ambient + attenuation * (spotEffect * diffuse + specular);
|
||||
// }
|
||||
|
||||
vec3 calc_lighting(vec3 position, vec3 normal, vec3 viewDir) {
|
||||
vec3 weight = vec3(0.0);
|
||||
for (int i = 0; i < MAX_NUM_OF_DIRECTIONAL_LIGHTS; i++) {
|
||||
if (i >= u_num_of_directional_lights) {
|
||||
break;
|
||||
}
|
||||
weight += calc_directional_light(u_directional_lights[i], normal, viewDir);
|
||||
}
|
||||
// for (int i = 0; i < MAX_NUM_OF_SPOT_LIGHTS; i++) {
|
||||
// if (i >= u_num_of_spot_lights) {
|
||||
// break;
|
||||
// }
|
||||
// weight += calc_spot_light(u_spot_lights[i], normal, position, viewDir);
|
||||
// }
|
||||
return weight;
|
||||
}
|
|
@ -1,6 +1,7 @@
|
|||
import * as THREE from '../../../core/three';
|
||||
import PolygonBuffer from '../../../geom/buffer/polygon';
|
||||
import PolygonMaterial from '../../../geom/material/polygonMaterial';
|
||||
import { generateLightingUniforms } from '../../../util/shaderModule';
|
||||
|
||||
export default function DrawPolygonFill(layerData, layer) {
|
||||
const style = layer.get('styleOptions');
|
||||
|
@ -9,7 +10,7 @@ export default function DrawPolygonFill(layerData, layer) {
|
|||
...style,
|
||||
activeColor: activeOption.fill
|
||||
};
|
||||
const { opacity, activeColor } = config;
|
||||
const { opacity, activeColor, lights } = config;
|
||||
const { attributes } = new PolygonBuffer({
|
||||
shape: layer.shape,
|
||||
layerData
|
||||
|
@ -21,9 +22,11 @@ export default function DrawPolygonFill(layerData, layer) {
|
|||
geometry.addAttribute('normal', new THREE.Float32BufferAttribute(attributes.normals, 3));
|
||||
const material = new PolygonMaterial({
|
||||
u_opacity: opacity,
|
||||
u_activeColor: activeColor
|
||||
u_activeColor: activeColor,
|
||||
...generateLightingUniforms(lights)
|
||||
}, {
|
||||
SHAPE: false
|
||||
SHAPE: false,
|
||||
LIGHTING: true
|
||||
});
|
||||
const fillPolygonMesh = new THREE.Mesh(geometry, material);
|
||||
return fillPolygonMesh;
|
||||
|
|
|
@ -178,7 +178,8 @@ export function wrapUniforms(uniforms) {
|
|||
|
||||
const DEFAULT_LIGHT = {
|
||||
type: 'directional',
|
||||
direction: [ 1, 10.5, 12 ],
|
||||
// direction: [ 1, 10.5, 12 ],
|
||||
direction: [ 0, -10.5, 1 ],
|
||||
ambient: [ 0.2, 0.2, 0.2 ],
|
||||
diffuse: [ 0.6, 0.6, 0.6 ],
|
||||
specular: [ 0.1, 0.1, 0.1 ]
|
||||
|
|
Loading…
Reference in New Issue