Add basic shader
This commit is contained in:
parent
2550e2e14f
commit
2235063a24
97
source/GLRender/BasicShader.ts
Normal file
97
source/GLRender/BasicShader.ts
Normal file
@ -0,0 +1,97 @@
|
|||||||
|
import { ObjectData } from "@Model/Renderer";
|
||||||
|
import { GLContext } from "./GLContext";
|
||||||
|
import { GLShader } from "./GLShader";
|
||||||
|
|
||||||
|
export { BasicsShader }
|
||||||
|
|
||||||
|
interface IBasicsShaderAttribute {
|
||||||
|
aPosition: ObjectData
|
||||||
|
}
|
||||||
|
|
||||||
|
interface IBasicsShaderUniform {
|
||||||
|
uRadius: ObjectData,
|
||||||
|
uMvp: ObjectData,
|
||||||
|
uPosition: ObjectData,
|
||||||
|
uColor: ObjectData
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 基础绘制 Shader
|
||||||
|
* @class BasicsShader
|
||||||
|
*/
|
||||||
|
class BasicsShader extends GLShader<IBasicsShaderAttribute, IBasicsShaderUniform>{
|
||||||
|
|
||||||
|
public onLoad(context: GLContext) {
|
||||||
|
|
||||||
|
super.onLoad(context);
|
||||||
|
|
||||||
|
// 顶点着色
|
||||||
|
const vertex = `
|
||||||
|
attribute vec3 aPosition;
|
||||||
|
|
||||||
|
uniform vec3 uRadius;
|
||||||
|
uniform mat4 uMvp;
|
||||||
|
uniform vec3 uPosition;
|
||||||
|
|
||||||
|
void main(){
|
||||||
|
gl_Position = uMvp * vec4(aPosition * uRadius + uPosition, 1.);
|
||||||
|
}
|
||||||
|
`;
|
||||||
|
|
||||||
|
// 片段着色
|
||||||
|
const fragment = `
|
||||||
|
precision lowp float;
|
||||||
|
|
||||||
|
uniform vec3 uColor;
|
||||||
|
|
||||||
|
void main(){
|
||||||
|
gl_FragColor = vec4(uColor, 1.);
|
||||||
|
}
|
||||||
|
`;
|
||||||
|
|
||||||
|
// 保存代码
|
||||||
|
this.setSource(vertex, fragment);
|
||||||
|
|
||||||
|
// 编译
|
||||||
|
this.compile();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 传递半径数据
|
||||||
|
*/
|
||||||
|
public radius(r: ObjectData){
|
||||||
|
this.gl.uniform3fv(
|
||||||
|
this.uniformLocate("uRadius"), r
|
||||||
|
);
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 坐标
|
||||||
|
*/
|
||||||
|
public position(position: ObjectData){
|
||||||
|
this.gl.uniform3fv(
|
||||||
|
this.uniformLocate("uPosition"), position
|
||||||
|
);
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 传递半径数据
|
||||||
|
*/
|
||||||
|
public mvp(mat: ObjectData, transpose: boolean = false){
|
||||||
|
this.gl.uniformMatrix4fv(
|
||||||
|
this.uniformLocate("uMvp"), transpose, mat
|
||||||
|
);
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 传递半径数据
|
||||||
|
*/
|
||||||
|
public color(rgb: ObjectData){
|
||||||
|
this.gl.uniform3fv(
|
||||||
|
this.uniformLocate("uColor"), rgb
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
@ -1,13 +1,21 @@
|
|||||||
import { ObjectID, ObjectData, ICommonParam } from "@Model/Renderer";
|
import { ObjectID, ObjectData, ICommonParam } from "@Model/Renderer";
|
||||||
import { BasicRenderer, IRendererParams } from "./BasicRenderer";
|
import { BasicRenderer, IRendererParams } from "./BasicRenderer";
|
||||||
|
import { BasicsShader } from "./BasicShader";
|
||||||
|
|
||||||
interface IClassicRendererParams {}
|
interface IClassicRendererParams {}
|
||||||
|
|
||||||
class ClassicRenderer extends BasicRenderer<{}, IClassicRendererParams> {
|
class ClassicRenderer extends BasicRenderer<{}, IClassicRendererParams> {
|
||||||
|
|
||||||
onLoad(param: Partial<IClassicRendererParams & IRendererParams>): void {
|
onLoad(param: Partial<IClassicRendererParams & IRendererParams>): void {
|
||||||
this.run();
|
|
||||||
|
// 自动调节分辨率
|
||||||
this.autoResize();
|
this.autoResize();
|
||||||
|
|
||||||
|
let shader = new BasicsShader();
|
||||||
|
!shader.isLoad && shader.onLoad(this.gl);
|
||||||
|
|
||||||
|
// 运行
|
||||||
|
this.run();
|
||||||
}
|
}
|
||||||
|
|
||||||
clean(id?: ObjectID | ObjectID[]): this {
|
clean(id?: ObjectID | ObjectID[]): this {
|
||||||
@ -22,7 +30,7 @@ class ClassicRenderer extends BasicRenderer<{}, IClassicRendererParams> {
|
|||||||
throw new Error("Method not implemented.");
|
throw new Error("Method not implemented.");
|
||||||
}
|
}
|
||||||
|
|
||||||
loop(): void {
|
loop(t: number): void {
|
||||||
this.cleanCanvas();
|
this.cleanCanvas();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -24,5 +24,7 @@ export abstract class GLContextObject<
|
|||||||
/**
|
/**
|
||||||
* 初始化生命周期
|
* 初始化生命周期
|
||||||
*/
|
*/
|
||||||
public abstract onLoad(context: GLContext): any;
|
public onLoad(context: GLContext): any {
|
||||||
|
this.gl = context;
|
||||||
|
};
|
||||||
}
|
}
|
@ -1,10 +1,14 @@
|
|||||||
import { EventType } from "@Model/Emitter";
|
import { EventType } from "@Model/Emitter";
|
||||||
import { GLContextObject } from "./GLContext"
|
import { GLContextObject } from "./GLContext"
|
||||||
|
|
||||||
|
type IAnyObject = Record<string, any>;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Shader类
|
* Shader类
|
||||||
*/
|
*/
|
||||||
abstract class GLShader<
|
abstract class GLShader<
|
||||||
|
A extends IAnyObject = {},
|
||||||
|
U extends IAnyObject = {},
|
||||||
E extends Record<EventType, any> = {}
|
E extends Record<EventType, any> = {}
|
||||||
> extends GLContextObject<E> {
|
> extends GLContextObject<E> {
|
||||||
|
|
||||||
@ -60,34 +64,36 @@ abstract class GLShader<
|
|||||||
this.fragmentShader = this.gl.createShader(this.gl.FRAGMENT_SHADER);
|
this.fragmentShader = this.gl.createShader(this.gl.FRAGMENT_SHADER);
|
||||||
|
|
||||||
// 绑定源代码
|
// 绑定源代码
|
||||||
this.gl.shaderSource(!this.vertexShader, this.vertexShaderSource);
|
this.gl.shaderSource(this.vertexShader!, this.vertexShaderSource);
|
||||||
this.gl.shaderSource(!this.fragmentShader, this.fragmentShaderSource);
|
this.gl.shaderSource(this.fragmentShader!, this.fragmentShaderSource);
|
||||||
|
|
||||||
// 编译
|
// 编译
|
||||||
this.gl.compileShader(!this.vertexShader);
|
this.gl.compileShader(this.vertexShader!);
|
||||||
this.gl.compileShader(!this.fragmentShader);
|
this.gl.compileShader(this.fragmentShader!);
|
||||||
|
|
||||||
// 检测编译错误
|
// 检测编译错误
|
||||||
if(!this.gl.getShaderParameter(!this.vertexShader, this.gl.COMPILE_STATUS)){
|
if(!this.gl.getShaderParameter(this.vertexShader!, this.gl.COMPILE_STATUS)){
|
||||||
console.error("vertex:\r\n" + this.gl.getShaderInfoLog(!this.vertexShader));
|
return console.error("vertex:\r\n" + this.gl.getShaderInfoLog(this.vertexShader!));
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!this.gl.getShaderParameter(!this.fragmentShader, this.gl.COMPILE_STATUS)){
|
if(!this.gl.getShaderParameter(this.fragmentShader!, this.gl.COMPILE_STATUS)){
|
||||||
console.error("fragment:\r\n" + this.gl.getShaderInfoLog(!this.fragmentShader));
|
return console.error("fragment:\r\n" + this.gl.getShaderInfoLog(this.fragmentShader!));
|
||||||
}
|
}
|
||||||
|
|
||||||
// 附加到程序
|
// 附加到程序
|
||||||
this.gl.attachShader(!this.program, !this.vertexShader);
|
this.gl.attachShader(this.program!, this.vertexShader!);
|
||||||
this.gl.attachShader(!this.program, !this.fragmentShader);
|
this.gl.attachShader(this.program!, this.fragmentShader!);
|
||||||
|
|
||||||
// 连接程序
|
// 连接程序
|
||||||
this.gl.linkProgram(!this.program);
|
this.gl.linkProgram(this.program!);
|
||||||
|
|
||||||
// 检测链接错误
|
// 检测链接错误
|
||||||
if(!this.gl.getProgramParameter(!this.program, this.gl.LINK_STATUS)){
|
if(!this.gl.getProgramParameter(this.program!, this.gl.LINK_STATUS)){
|
||||||
console.error("link:\r\n" + this.gl.getProgramInfoLog(!this.program));
|
return console.error("link:\r\n" + this.gl.getProgramInfoLog(this.program!));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
console.log("shader compile success");
|
||||||
|
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -104,15 +110,15 @@ abstract class GLShader<
|
|||||||
/**
|
/**
|
||||||
* 获取 attribLocation
|
* 获取 attribLocation
|
||||||
*/
|
*/
|
||||||
public attribLocate(attr: string){
|
public attribLocate<T extends keyof A>(attr: T){
|
||||||
|
|
||||||
// 获取缓存
|
// 获取缓存
|
||||||
let cache = this.attribLocationCache.get(attr);
|
let cache = this.attribLocationCache.get(attr as string);
|
||||||
|
|
||||||
// 缓存搜索
|
// 缓存搜索
|
||||||
if (cache === undefined || cache <= -1){
|
if (cache === undefined || cache <= -1){
|
||||||
|
|
||||||
cache = this.gl.getAttribLocation(!this.program, attr);
|
cache = this.gl.getAttribLocation(!this.program, attr as string);
|
||||||
|
|
||||||
if (cache === undefined || cache <= -1) {
|
if (cache === undefined || cache <= -1) {
|
||||||
console.error("Attrib: can not get locate of " + attr);
|
console.error("Attrib: can not get locate of " + attr);
|
||||||
@ -120,7 +126,7 @@ abstract class GLShader<
|
|||||||
this.gl.enableVertexAttribArray(cache);
|
this.gl.enableVertexAttribArray(cache);
|
||||||
}
|
}
|
||||||
|
|
||||||
this.attribLocationCache.set(attr, cache);
|
this.attribLocationCache.set(attr as string, cache);
|
||||||
|
|
||||||
return cache;
|
return cache;
|
||||||
}
|
}
|
||||||
@ -136,19 +142,19 @@ abstract class GLShader<
|
|||||||
/**
|
/**
|
||||||
* 获取 attribLocation
|
* 获取 attribLocation
|
||||||
*/
|
*/
|
||||||
public uniformLocate(uni: string) {
|
public uniformLocate<T extends keyof U>(uni: T) {
|
||||||
|
|
||||||
// 获取缓存
|
// 获取缓存
|
||||||
let cache: WebGLUniformLocation | null = this.uniformLocationCache.get(uni) as any;
|
let cache: WebGLUniformLocation | null = this.uniformLocationCache.get(uni as string) as any;
|
||||||
if (cache === undefined) cache = null;
|
if (cache === undefined) cache = null;
|
||||||
|
|
||||||
// 缓存搜索
|
// 缓存搜索
|
||||||
if (!cache) {
|
if (!cache) {
|
||||||
|
|
||||||
cache = this.gl.getUniformLocation(!this.program, uni);
|
cache = this.gl.getUniformLocation(!this.program, uni as string);
|
||||||
if (!cache) console.error("Uniform: can not get locate of " + uni);
|
if (!cache) console.error("Uniform: can not get locate of " + uni);
|
||||||
|
|
||||||
this.uniformLocationCache.set(uni, cache as any);
|
this.uniformLocationCache.set(uni as string, cache as any);
|
||||||
|
|
||||||
return cache;
|
return cache;
|
||||||
}
|
}
|
||||||
|
@ -45,7 +45,7 @@ type ObjectID = Symbol | string | number;
|
|||||||
/**
|
/**
|
||||||
* 接收的数据类型
|
* 接收的数据类型
|
||||||
*/
|
*/
|
||||||
type ObjectData = Array<number> | Float32Array | Float64Array;
|
type ObjectData = Array<number> | Float32Array;
|
||||||
|
|
||||||
interface IRendererConstructor<
|
interface IRendererConstructor<
|
||||||
M extends IAnyObject = {}
|
M extends IAnyObject = {}
|
||||||
|
Loading…
Reference in New Issue
Block a user