| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <meta http-equiv="X-UA-Compatible" content="IE=edge"> |
| <meta name="viewport" content="width=device-width, initial-scale=1.0"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| <style> |
| |
| </style> |
| </head> |
| |
| <body> |
| |
| <canvas id="webgpu" width="500" height="500"></canvas> |
| <script type="module"> |
| |
| import { vertex, fragment } from './shader.js' |
| |
| |
| const adapter = await navigator.gpu.requestAdapter(); |
| const device = await adapter.requestDevice(); |
| const canvas = document.getElementById('webgpu'); |
| |
| |
| const context = canvas.getContext('webgpu'); |
| const format = navigator.gpu.getPreferredCanvasFormat(); |
| context.configure({ |
| device: device, |
| format: format, |
| }); |
| |
| |
| |
| |
| |
| const vertexArray = new Float32Array([ |
| |
| -0.3, -0.5, 0.0, |
| 0.3, -0.5, 0.0, |
| 0.3, 0.5, 0.0, |
| |
| -0.3, -0.5, 0.0, |
| 0.3, 0.5, 0.0, |
| -0.3, 0.5, 0.0, |
| ]); |
| const vertexBuffer = device.createBuffer({ |
| size: vertexArray.byteLength, |
| usage: GPUBufferUsage.VERTEX | GPUBufferUsage.COPY_DST, |
| }); |
| device.queue.writeBuffer(vertexBuffer, 0, vertexArray); |
| |
| |
| |
| const pipeline = device.createRenderPipeline({ |
| layout: 'auto', |
| vertex: { |
| module: device.createShaderModule({ code: vertex }), |
| entryPoint: "main", |
| buffers: [ |
| { |
| arrayStride: 3 * 4, |
| attributes: [{ |
| shaderLocation: 0, |
| format: "float32x3", |
| offset: 0 |
| }] |
| } |
| ] |
| }, |
| fragment: { |
| module: device.createShaderModule({ code: fragment }), |
| entryPoint: "main", |
| targets: [{ |
| format: format |
| }] |
| }, |
| primitive: { |
| topology: "triangle-list", |
| } |
| }); |
| |
| |
| const commandEncoder = device.createCommandEncoder(); |
| |
| const renderPass = commandEncoder.beginRenderPass({ |
| colorAttachments: [{ |
| view: context.getCurrentTexture().createView(), |
| storeOp: 'store', |
| loadOp: 'clear', |
| }] |
| }); |
| renderPass.setPipeline(pipeline); |
| |
| renderPass.setVertexBuffer(0, vertexBuffer); |
| renderPass.draw(6); |
| renderPass.end(); |
| const commandBuffer = commandEncoder.finish(); |
| device.queue.submit([commandBuffer]); |
| </script> |
| </body> |
| |
| </html> |
| |
| const vertex = ` |
| @vertex |
| fn main(@location(0) pos: vec3<f32>) -> @builtin(position) vec4<f32> { |
| return vec4<f32>(pos,1.0); |
| } |
| `; |
| |
| |
| const fragment = ` |
| @fragment |
| fn main(@builtin(position) fragCoord : vec4<f32>) -> @location(0) vec4<f32> { |
| var x = fragCoord.x;//片元屏幕坐标x |
| var y = fragCoord.y;//片元屏幕坐标y |
| // fragCoord.z; |
| if(x < 250.0){ |
| // 片元x屏幕坐标小于250,片元设置为红色 |
| return vec4<f32>(1.0, 0.0, 0.0, 1.0); |
| }else{ |
| // 片元x屏幕坐标不小于250,片元设置为绿色 |
| return vec4<f32>(0.0, 1.0, 0.0, 1.0); |
| } |
| |
| // 左上角红色,其他区域绿色 |
| // if(x < 250.0 && y < 250.0){ |
| // return vec4<f32>(1.0, 0.0, 0.0, 1.0); |
| // }else{ |
| // return vec4<f32>(0.0, 1.0, 0.0, 1.0); |
| // } |
| } |
| `; |
| |
| export { vertex, fragment }; |
| |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <meta http-equiv="X-UA-Compatible" content="IE=edge"> |
| <meta name="viewport" content="width=device-width, initial-scale=1.0"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <canvas id="webgpu" width="500" height="500"></canvas> |
| <script type="module"> |
| |
| import { vertex, fragment } from './shader.js' |
| |
| |
| const adapter = await navigator.gpu.requestAdapter(); |
| const device = await adapter.requestDevice(); |
| const canvas = document.getElementById('webgpu'); |
| const context = canvas.getContext('webgpu'); |
| const format = navigator.gpu.getPreferredCanvasFormat(); |
| context.configure({ |
| device: device, |
| format: format, |
| }); |
| |
| |
| |
| |
| |
| const vertexArray = new Float32Array([ |
| 1.0, 0.0, 0.0, |
| 0.0, 1.0, 0.0, |
| 0.0, 0.0, 0.0, |
| ]); |
| const vertexBuffer = device.createBuffer({ |
| size: vertexArray.byteLength, |
| usage: GPUBufferUsage.VERTEX | GPUBufferUsage.COPY_DST, |
| }); |
| device.queue.writeBuffer(vertexBuffer, 0, vertexArray); |
| |
| |
| |
| const pipeline = device.createRenderPipeline({ |
| layout: 'auto', |
| vertex: { |
| module: device.createShaderModule({ code: vertex }), |
| entryPoint: "main", |
| buffers: [ |
| { |
| arrayStride: 3 * 4, |
| attributes: [{ |
| shaderLocation: 0, |
| format: "float32x3", |
| offset: 0 |
| }] |
| } |
| ] |
| }, |
| fragment: { |
| module: device.createShaderModule({ code: fragment }), |
| entryPoint: "main", |
| targets: [{ |
| format: format |
| }] |
| }, |
| primitive: { |
| topology: "triangle-list", |
| } |
| }); |
| |
| |
| const commandEncoder = device.createCommandEncoder(); |
| |
| const renderPass = commandEncoder.beginRenderPass({ |
| colorAttachments: [{ |
| view: context.getCurrentTexture().createView(), |
| storeOp: 'store', |
| loadOp: 'clear', |
| }] |
| }); |
| renderPass.setPipeline(pipeline); |
| |
| renderPass.setVertexBuffer(0, vertexBuffer); |
| renderPass.draw(3); |
| renderPass.end(); |
| const commandBuffer = commandEncoder.finish(); |
| device.queue.submit([commandBuffer]); |
| </script> |
| </body> |
| |
| </html> |
| |
| const vertex = ` |
| @vertex |
| fn main(@location(0) pos: vec3<f32>) -> @builtin(position) vec4<f32> { |
| return vec4<f32>(pos,1.0); |
| } |
| ` |
| |
| |
| const fragment = ` |
| @fragment |
| fn main(@builtin(position) fragCoord : vec4<f32>) -> @location(0) vec4<f32> { |
| var x = fragCoord.x;//片元屏幕坐标x |
| var y = fragCoord.y;//片元屏幕坐标y |
| // 渐变色 |
| var per: f32 = (x-250.0)/250.0; |
| return vec4<f32>(per, 0.0, 1.0-per, 1.0); |
| } |
| ` |
| |
| export { vertex, fragment } |
| |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <title>Three.js中文网:www.webgl3d.cn</title> |
| </head> |
| |
| <body> |
| <script> |
| let i = 0; |
| |
| function render() { |
| i += 1; |
| console.log(i); |
| } |
| render(); |
| </script> |
| </body> |
| |
| </html> |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <title>Three.js中文网:www.webgl3d.cn</title> |
| </head> |
| |
| <body> |
| <script> |
| |
| |
| let i = 0; |
| function render() { |
| i+=1; |
| console.log('执行次数'+i); |
| requestAnimationFrame(render); |
| } |
| render(); |
| </script> |
| </body> |
| |
| </html> |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <meta http-equiv="X-UA-Compatible" content="IE=edge"> |
| <meta name="viewport" content="width=device-width, initial-scale=1.0"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <canvas id="webgpu" width="500" height="500"></canvas> |
| <script type="module"> |
| |
| import * as glMatrix from '../../gl-matrix/index.js' |
| |
| import { vertex, fragment } from './shader.js' |
| |
| |
| const adapter = await navigator.gpu.requestAdapter(); |
| const device = await adapter.requestDevice(); |
| const canvas = document.getElementById('webgpu'); |
| const context = canvas.getContext('webgpu'); |
| const format = navigator.gpu.getPreferredCanvasFormat(); |
| context.configure({ |
| device: device, |
| format: format, |
| }); |
| |
| |
| const vertexArray = new Float32Array([ |
| |
| -0.3, -0.5, 0.0, |
| 0.3, -0.5, 0.0, |
| 0.3, 0.5, 0.0, |
| |
| -0.3, -0.5, 0.0, |
| 0.3, 0.5, 0.0, |
| -0.3, 0.5, 0.0, |
| ]); |
| const vertexBuffer = device.createBuffer({ |
| size: vertexArray.byteLength, |
| usage: GPUBufferUsage.VERTEX | GPUBufferUsage.COPY_DST, |
| }); |
| device.queue.writeBuffer(vertexBuffer, 0, vertexArray); |
| |
| |
| |
| const pipeline = device.createRenderPipeline({ |
| layout: 'auto', |
| vertex: { |
| module: device.createShaderModule({ code: vertex }), |
| entryPoint: "main", |
| buffers: [ |
| { |
| arrayStride: 3 * 4, |
| attributes: [{ |
| shaderLocation: 0, |
| format: "float32x3", |
| offset: 0 |
| }] |
| } |
| ] |
| }, |
| fragment: { |
| module: device.createShaderModule({ code: fragment }), |
| entryPoint: "main", |
| targets: [{ |
| format: format |
| }] |
| }, |
| primitive: { |
| topology: "triangle-list", |
| } |
| }); |
| |
| |
| const modelMatrix = glMatrix.mat4.create(); |
| |
| glMatrix.mat4.rotateZ(modelMatrix, modelMatrix, Math.PI/6); |
| |
| |
| |
| |
| const modelMatrixBuffer = device.createBuffer({ |
| size: modelMatrix.byteLength, |
| usage: GPUBufferUsage.UNIFORM | GPUBufferUsage.COPY_DST |
| }); |
| device.queue.writeBuffer(modelMatrixBuffer, 0, modelMatrix); |
| |
| |
| |
| const bindGroup = device.createBindGroup({ |
| |
| layout: pipeline.getBindGroupLayout(0), |
| |
| entries: [ |
| { |
| |
| binding: 0, |
| resource: { buffer: modelMatrixBuffer } |
| } |
| ] |
| }); |
| |
| |
| const commandEncoder = device.createCommandEncoder(); |
| |
| const renderPass = commandEncoder.beginRenderPass({ |
| colorAttachments: [{ |
| view: context.getCurrentTexture().createView(), |
| storeOp: 'store', |
| |
| loadOp: 'clear', |
| }] |
| }); |
| renderPass.setPipeline(pipeline); |
| |
| renderPass.setVertexBuffer(0, vertexBuffer); |
| |
| renderPass.setBindGroup(0, bindGroup); |
| renderPass.draw(6); |
| renderPass.end(); |
| const commandBuffer = commandEncoder.finish(); |
| device.queue.submit([commandBuffer]); |
| </script> |
| </body> |
| |
| </html> |
| |
| const vertex = ` |
| @group(0) @binding(0) var<uniform> modelMatrix:mat4x4<f32>; |
| @vertex |
| fn main(@location(0) pos: vec3<f32>) -> @builtin(position) vec4<f32> { |
| return modelMatrix * vec4<f32>(pos,1.0); |
| } |
| ` |
| |
| |
| const fragment = ` |
| @fragment |
| fn main() -> @location(0) vec4<f32> { |
| return vec4<f32>(1.0, 0.0, 0.0, 1.0); |
| } |
| ` |
| |
| export { vertex, fragment } |
| |
| |
| |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <meta http-equiv="X-UA-Compatible" content="IE=edge"> |
| <meta name="viewport" content="width=device-width, initial-scale=1.0"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <canvas id="webgpu" width="500" height="500"></canvas> |
| <script type="module"> |
| |
| import * as glMatrix from '../../gl-matrix/index.js' |
| |
| import { vertex, fragment } from './shader.js' |
| |
| |
| const adapter = await navigator.gpu.requestAdapter(); |
| const device = await adapter.requestDevice(); |
| const canvas = document.getElementById('webgpu'); |
| const context = canvas.getContext('webgpu'); |
| const format = navigator.gpu.getPreferredCanvasFormat(); |
| context.configure({ |
| device: device, |
| format: format, |
| }); |
| |
| |
| |
| const vertexArray = new Float32Array([ |
| |
| -0.3, -0.5, 0.0, |
| 0.3, -0.5, 0.0, |
| 0.3, 0.5, 0.0, |
| |
| -0.3, -0.5, 0.0, |
| 0.3, 0.5, 0.0, |
| -0.3, 0.5, 0.0, |
| ]); |
| const vertexBuffer = device.createBuffer({ |
| size: vertexArray.byteLength, |
| usage: GPUBufferUsage.VERTEX | GPUBufferUsage.COPY_DST, |
| }); |
| device.queue.writeBuffer(vertexBuffer, 0, vertexArray); |
| |
| |
| |
| const pipeline = device.createRenderPipeline({ |
| layout: 'auto', |
| vertex: { |
| module: device.createShaderModule({ code: vertex }), |
| entryPoint: "main", |
| buffers: [ |
| { |
| arrayStride: 3 * 4, |
| attributes: [{ |
| shaderLocation: 0, |
| format: "float32x3", |
| offset: 0 |
| }] |
| } |
| ] |
| }, |
| fragment: { |
| module: device.createShaderModule({ code: fragment }), |
| entryPoint: "main", |
| targets: [{ |
| format: format |
| }] |
| }, |
| primitive: { |
| topology: "triangle-list", |
| } |
| }); |
| |
| |
| const modelMatrix = glMatrix.mat4.create(); |
| |
| const modelMatrixBuffer = device.createBuffer({ |
| size: modelMatrix.byteLength, |
| usage: GPUBufferUsage.UNIFORM | GPUBufferUsage.COPY_DST |
| }); |
| device.queue.writeBuffer(modelMatrixBuffer, 0, modelMatrix); |
| |
| |
| |
| const bindGroup = device.createBindGroup({ |
| layout: pipeline.getBindGroupLayout(0), |
| entries: [ |
| { |
| |
| binding: 0, |
| resource: { buffer: modelMatrixBuffer } |
| } |
| ] |
| }); |
| |
| |
| let angle = 0.0; |
| function render() { |
| angle += 0.05; |
| const modelMatrix = glMatrix.mat4.create(); |
| |
| glMatrix.mat4.rotateZ(modelMatrix, modelMatrix, angle); |
| |
| device.queue.writeBuffer(modelMatrixBuffer, 0, modelMatrix) |
| |
| |
| const commandEncoder = device.createCommandEncoder(); |
| |
| const renderPass = commandEncoder.beginRenderPass({ |
| colorAttachments: [{ |
| view: context.getCurrentTexture().createView(), |
| storeOp: 'store', |
| |
| loadOp: 'clear', |
| }] |
| }); |
| renderPass.setPipeline(pipeline); |
| |
| renderPass.setVertexBuffer(0, vertexBuffer); |
| |
| renderPass.setBindGroup(0, bindGroup); |
| renderPass.draw(6); |
| renderPass.end(); |
| const commandBuffer = commandEncoder.finish(); |
| device.queue.submit([commandBuffer]); |
| |
| requestAnimationFrame(render); |
| } |
| render() |
| </script> |
| </body> |
| |
| </html> |
| |
| const vertex = ` |
| @group(0) @binding(0) var<uniform> modelMatrix:mat4x4<f32>; |
| @vertex |
| fn main(@location(0) pos: vec3<f32>) -> @builtin(position) vec4<f32> { |
| return modelMatrix * vec4<f32>(pos,1.0); |
| } |
| ` |
| |
| |
| const fragment = ` |
| @fragment |
| fn main() -> @location(0) vec4<f32> { |
| return vec4<f32>(1.0, 0.0, 0.0, 1.0); |
| } |
| ` |
| |
| export { vertex, fragment } |
| |
| |
| |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <meta http-equiv="X-UA-Compatible" content="IE=edge"> |
| <meta name="viewport" content="width=device-width, initial-scale=1.0"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <canvas id="webgpu" width="500" height="500"></canvas> |
| <script type="module"> |
| |
| import * as glMatrix from '../../gl-matrix/index.js' |
| |
| import { vertex, fragment } from './shader.js' |
| |
| |
| const adapter = await navigator.gpu.requestAdapter(); |
| const device = await adapter.requestDevice(); |
| const canvas = document.getElementById('webgpu'); |
| const context = canvas.getContext('webgpu'); |
| const format = navigator.gpu.getPreferredCanvasFormat(); |
| context.configure({ |
| device: device, |
| format: format, |
| }); |
| |
| |
| |
| const vertexArray = new Float32Array([ |
| |
| 0.0, 0.0, 0.0, |
| 1.0, 0.0, 0.0, |
| 0.0, 1.0, 0.0, |
| ]); |
| const vertexBuffer = device.createBuffer({ |
| size: vertexArray.byteLength, |
| usage: GPUBufferUsage.VERTEX | GPUBufferUsage.COPY_DST, |
| }); |
| device.queue.writeBuffer(vertexBuffer, 0, vertexArray); |
| |
| |
| |
| const pipeline = device.createRenderPipeline({ |
| layout: 'auto', |
| vertex: { |
| module: device.createShaderModule({ code: vertex }), |
| entryPoint: "main", |
| buffers: [ |
| { |
| arrayStride: 3 * 4, |
| attributes: [{ |
| shaderLocation: 0, |
| format: "float32x3", |
| offset: 0 |
| }] |
| } |
| ] |
| }, |
| fragment: { |
| module: device.createShaderModule({ code: fragment }), |
| entryPoint: "main", |
| targets: [{ |
| format: format |
| }] |
| }, |
| primitive: { |
| topology: "triangle-list", |
| |
| } |
| }); |
| |
| |
| const mat4Array = glMatrix.mat4.create(); |
| |
| glMatrix.mat4.translate(mat4Array, mat4Array, [-1, -1, 0]); |
| |
| const mat4Buffer = device.createBuffer({ |
| size: mat4Array.byteLength, |
| usage: GPUBufferUsage.UNIFORM | GPUBufferUsage.COPY_DST |
| }); |
| |
| device.queue.writeBuffer(mat4Buffer, 0, mat4Array); |
| |
| |
| |
| const bindGroup = device.createBindGroup({ |
| |
| layout: pipeline.getBindGroupLayout(0), |
| |
| entries: [ |
| { |
| |
| binding: 0, |
| resource: { buffer: mat4Buffer } |
| } |
| ] |
| }); |
| |
| |
| const commandEncoder = device.createCommandEncoder(); |
| |
| const renderPass = commandEncoder.beginRenderPass({ |
| colorAttachments: [{ |
| view: context.getCurrentTexture().createView(), |
| storeOp: 'store', |
| |
| loadOp: 'clear', |
| }] |
| }); |
| renderPass.setPipeline(pipeline); |
| |
| renderPass.setVertexBuffer(0, vertexBuffer); |
| |
| renderPass.setBindGroup(0, bindGroup); |
| renderPass.draw(3); |
| renderPass.end(); |
| const commandBuffer = commandEncoder.finish(); |
| device.queue.submit([commandBuffer]); |
| </script> |
| </body> |
| |
| </html> |
| |
| const vertex = ` |
| // uniform关键字辅助var声明一个4x4矩阵变量 |
| //@group(0)的参数0对应webgpu代码.getBindGroupLayout(0)参数0 |
| //@binding(0)的参数对应webgpu代码.binding的值,保持一致,比如都是0 |
| @group(0) @binding(0) var<uniform> modelMatrix:mat4x4<f32>; |
| @vertex |
| fn main(@location(0) pos: vec3<f32>) -> @builtin(position) vec4<f32> { |
| return modelMatrix * vec4<f32>(pos,1.0); |
| } |
| ` |
| |
| |
| const fragment = ` |
| @fragment |
| fn main() -> @location(0) vec4<f32> { |
| return vec4<f32>(1.0, 0.0, 0.0, 1.0); |
| } |
| ` |
| |
| export { vertex, fragment } |
| |
| |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <meta http-equiv="X-UA-Compatible" content="IE=edge"> |
| <meta name="viewport" content="width=device-width, initial-scale=1.0"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <canvas id="webgpu" width="500" height="500"></canvas> |
| <script type="module"> |
| |
| import * as glMatrix from '../../gl-matrix/index.js' |
| |
| import { vertex, fragment } from './shader.js' |
| |
| |
| const adapter = await navigator.gpu.requestAdapter(); |
| const device = await adapter.requestDevice(); |
| const canvas = document.getElementById('webgpu'); |
| const context = canvas.getContext('webgpu'); |
| const format = navigator.gpu.getPreferredCanvasFormat(); |
| context.configure({ |
| device: device, |
| format: format, |
| }); |
| |
| |
| |
| const vertexArray = new Float32Array([ |
| |
| 0.0, 0.0, 0.0, |
| 1.0, 0.0, 0.0, |
| 0.0, 1.0, 0.0, |
| ]); |
| const vertexBuffer = device.createBuffer({ |
| size: vertexArray.byteLength, |
| usage: GPUBufferUsage.VERTEX | GPUBufferUsage.COPY_DST, |
| }); |
| device.queue.writeBuffer(vertexBuffer, 0, vertexArray); |
| |
| |
| |
| const pipeline = device.createRenderPipeline({ |
| layout: 'auto', |
| vertex: { |
| module: device.createShaderModule({ code: vertex }), |
| entryPoint: "main", |
| buffers: [ |
| { |
| arrayStride: 3 * 4, |
| attributes: [{ |
| shaderLocation: 0, |
| format: "float32x3", |
| offset: 0 |
| }] |
| } |
| ] |
| }, |
| fragment: { |
| module: device.createShaderModule({ code: fragment }), |
| entryPoint: "main", |
| targets: [{ |
| format: format |
| }] |
| }, |
| primitive: { |
| topology: "triangle-list", |
| |
| } |
| }); |
| |
| |
| const modelMatrix = glMatrix.mat4.create(); |
| |
| glMatrix.mat4.translate(modelMatrix, modelMatrix, [-1, -1, 0]); |
| |
| glMatrix.mat4.scale(modelMatrix, modelMatrix, [0.5, 0.5, 1]); |
| |
| |
| const modelMatrixBuffer = device.createBuffer({ |
| size: modelMatrix.byteLength, |
| usage: GPUBufferUsage.UNIFORM | GPUBufferUsage.COPY_DST |
| }); |
| device.queue.writeBuffer(modelMatrixBuffer, 0, modelMatrix); |
| |
| |
| |
| const bindGroup = device.createBindGroup({ |
| |
| layout: pipeline.getBindGroupLayout(0), |
| |
| entries: [ |
| { |
| binding: 0, |
| resource: { buffer: modelMatrixBuffer } |
| } |
| ] |
| }); |
| |
| |
| const commandEncoder = device.createCommandEncoder(); |
| |
| const renderPass = commandEncoder.beginRenderPass({ |
| colorAttachments: [{ |
| view: context.getCurrentTexture().createView(), |
| storeOp: 'store', |
| |
| loadOp: 'clear', |
| }] |
| }); |
| renderPass.setPipeline(pipeline); |
| |
| renderPass.setVertexBuffer(0, vertexBuffer); |
| |
| renderPass.setBindGroup(0, bindGroup); |
| renderPass.draw(3); |
| renderPass.end(); |
| const commandBuffer = commandEncoder.finish(); |
| device.queue.submit([commandBuffer]); |
| </script> |
| </body> |
| |
| </html> |
| |
| const vertex = ` |
| @group(0) @binding(0) var<uniform> modelMatrix:mat4x4<f32>; |
| @vertex |
| fn main(@location(0) pos: vec3<f32>) -> @builtin(position) vec4<f32> { |
| return modelMatrix * vec4<f32>(pos,1.0); |
| } |
| ` |
| |
| |
| const fragment = ` |
| @fragment |
| fn main() -> @location(0) vec4<f32> { |
| return vec4<f32>(1.0, 0.0, 0.0, 1.0); |
| } |
| ` |
| |
| export { vertex, fragment } |
| |
| |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <meta http-equiv="X-UA-Compatible" content="IE=edge"> |
| <meta name="viewport" content="width=device-width, initial-scale=1.0"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <canvas id="webgpu" width="500" height="500"></canvas> |
| <script type="module"> |
| |
| import * as glMatrix from '../../gl-matrix/index.js' |
| |
| import { vertex, fragment } from './shader.js' |
| |
| |
| const adapter = await navigator.gpu.requestAdapter(); |
| const device = await adapter.requestDevice(); |
| const canvas = document.getElementById('webgpu'); |
| const context = canvas.getContext('webgpu'); |
| const format = navigator.gpu.getPreferredCanvasFormat(); |
| context.configure({ |
| device: device, |
| format: format, |
| }); |
| |
| |
| |
| const vertexArray = new Float32Array([ |
| |
| 0.0, 0.0, 0.0, |
| 1.0, 0.0, 0.0, |
| 0.0, 1.0, 0.0, |
| ]); |
| const vertexBuffer = device.createBuffer({ |
| size: vertexArray.byteLength, |
| usage: GPUBufferUsage.VERTEX | GPUBufferUsage.COPY_DST, |
| }); |
| device.queue.writeBuffer(vertexBuffer, 0, vertexArray); |
| |
| |
| |
| const pipeline = device.createRenderPipeline({ |
| layout: 'auto', |
| vertex: { |
| module: device.createShaderModule({ code: vertex }), |
| entryPoint: "main", |
| buffers: [ |
| { |
| arrayStride: 3 * 4, |
| attributes: [{ |
| shaderLocation: 0, |
| format: "float32x3", |
| offset: 0 |
| }] |
| } |
| ] |
| }, |
| fragment: { |
| module: device.createShaderModule({ code: fragment }), |
| entryPoint: "main", |
| targets: [{ |
| format: format |
| }] |
| }, |
| primitive: { |
| topology: "triangle-list", |
| |
| } |
| }); |
| |
| |
| const modelMatrix = glMatrix.mat4.create(); |
| |
| glMatrix.mat4.scale(modelMatrix, modelMatrix, [0.5, 0.5, 1]); |
| |
| glMatrix.mat4.translate(modelMatrix, modelMatrix, [-1, -1, 0]); |
| |
| const modelMatrixBuffer = device.createBuffer({ |
| size: modelMatrix.byteLength, |
| usage: GPUBufferUsage.UNIFORM | GPUBufferUsage.COPY_DST |
| }); |
| device.queue.writeBuffer(modelMatrixBuffer, 0, modelMatrix); |
| |
| |
| |
| const bindGroup = device.createBindGroup({ |
| |
| layout: pipeline.getBindGroupLayout(0), |
| |
| entries: [ |
| { |
| binding: 0, |
| resource: { buffer: modelMatrixBuffer } |
| } |
| ] |
| }); |
| |
| |
| const commandEncoder = device.createCommandEncoder(); |
| |
| const renderPass = commandEncoder.beginRenderPass({ |
| colorAttachments: [{ |
| view: context.getCurrentTexture().createView(), |
| storeOp: 'store', |
| |
| loadOp: 'clear', |
| }] |
| }); |
| renderPass.setPipeline(pipeline); |
| |
| renderPass.setVertexBuffer(0, vertexBuffer); |
| |
| renderPass.setBindGroup(0, bindGroup); |
| renderPass.draw(3); |
| renderPass.end(); |
| const commandBuffer = commandEncoder.finish(); |
| device.queue.submit([commandBuffer]); |
| </script> |
| </body> |
| |
| </html> |
| |
| const vertex = ` |
| @group(0) @binding(0) var<uniform> modelMatrix:mat4x4<f32>; |
| @vertex |
| fn main(@location(0) pos: vec3<f32>) -> @builtin(position) vec4<f32> { |
| return modelMatrix * vec4<f32>(pos,1.0); |
| } |
| ` |
| |
| |
| const fragment = ` |
| @fragment |
| fn main() -> @location(0) vec4<f32> { |
| return vec4<f32>(1.0, 0.0, 0.0, 1.0); |
| } |
| ` |
| |
| export { vertex, fragment } |
| |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <meta http-equiv="X-UA-Compatible" content="IE=edge"> |
| <meta name="viewport" content="width=device-width, initial-scale=1.0"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <canvas id="webgpu" width="500" height="500"></canvas> |
| <script type="module"> |
| |
| import * as glMatrix from '../../gl-matrix/index.js' |
| |
| import { vertex, fragment } from './shader.js' |
| |
| |
| const adapter = await navigator.gpu.requestAdapter(); |
| const device = await adapter.requestDevice(); |
| const canvas = document.getElementById('webgpu'); |
| const context = canvas.getContext('webgpu'); |
| const format = navigator.gpu.getPreferredCanvasFormat(); |
| context.configure({ |
| device: device, |
| format: format, |
| }); |
| |
| |
| |
| const vertexArray = new Float32Array([ |
| |
| 0.0, 0.0, 0.0, |
| 1.0, 0.0, 0.0, |
| 0.0, 1.0, 0.0, |
| ]); |
| const vertexBuffer = device.createBuffer({ |
| size: vertexArray.byteLength, |
| usage: GPUBufferUsage.VERTEX | GPUBufferUsage.COPY_DST, |
| }); |
| device.queue.writeBuffer(vertexBuffer, 0, vertexArray); |
| |
| |
| |
| const pipeline = device.createRenderPipeline({ |
| layout: 'auto', |
| vertex: { |
| module: device.createShaderModule({ code: vertex }), |
| entryPoint: "main", |
| buffers: [ |
| { |
| arrayStride: 3 * 4, |
| attributes: [{ |
| shaderLocation: 0, |
| format: "float32x3", |
| offset: 0 |
| }] |
| } |
| ] |
| }, |
| fragment: { |
| module: device.createShaderModule({ code: fragment }), |
| entryPoint: "main", |
| targets: [{ |
| format: format |
| }] |
| }, |
| primitive: { |
| topology: "triangle-list", |
| |
| } |
| }); |
| |
| |
| const mat4Array = glMatrix.mat4.create(); |
| |
| glMatrix.mat4.scale(mat4Array, mat4Array, [0.5, 0.5, 1]); |
| |
| const mat4Buffer = device.createBuffer({ |
| size: mat4Array.byteLength, |
| usage: GPUBufferUsage.UNIFORM | GPUBufferUsage.COPY_DST |
| }); |
| |
| device.queue.writeBuffer(mat4Buffer, 0, mat4Array); |
| |
| |
| |
| const bindGroup = device.createBindGroup({ |
| |
| layout: pipeline.getBindGroupLayout(0), |
| |
| entries: [ |
| { |
| |
| binding: 0, |
| resource: { buffer: mat4Buffer } |
| } |
| ] |
| }); |
| |
| |
| const commandEncoder = device.createCommandEncoder(); |
| |
| const renderPass = commandEncoder.beginRenderPass({ |
| colorAttachments: [{ |
| view: context.getCurrentTexture().createView(), |
| storeOp: 'store', |
| |
| loadOp: 'clear', |
| }] |
| }); |
| renderPass.setPipeline(pipeline); |
| |
| renderPass.setVertexBuffer(0, vertexBuffer); |
| |
| renderPass.setBindGroup(0, bindGroup); |
| renderPass.draw(3); |
| renderPass.end(); |
| const commandBuffer = commandEncoder.finish(); |
| device.queue.submit([commandBuffer]); |
| </script> |
| </body> |
| |
| </html> |
| |
| const vertex = ` |
| // uniform关键字辅助var声明一个4x4矩阵变量 |
| //@group(0)的参数0对应webgpu代码.getBindGroupLayout(0)参数0 |
| //@binding(0)的参数对应webgpu代码.binding的值,保持一致,比如都是0 |
| @group(0) @binding(0) var<uniform> S:mat4x4<f32>; |
| @vertex |
| fn main(@location(0) pos: vec3<f32>) -> @builtin(position) vec4<f32> { |
| return S * vec4<f32>(pos,1.0); |
| } |
| ` |
| |
| |
| const fragment = ` |
| @fragment |
| fn main() -> @location(0) vec4<f32> { |
| return vec4<f32>(1.0, 0.0, 0.0, 1.0); |
| } |
| ` |
| |
| export { vertex, fragment } |
| |
| |
| |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <meta http-equiv="X-UA-Compatible" content="IE=edge"> |
| <meta name="viewport" content="width=device-width, initial-scale=1.0"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <canvas id="webgpu" width="500" height="500"></canvas> |
| <script type="module"> |
| |
| import * as glMatrix from '../gl-matrix/index.js' |
| |
| import { vertex, fragment } from './shader.js' |
| |
| |
| const adapter = await navigator.gpu.requestAdapter(); |
| const device = await adapter.requestDevice(); |
| const canvas = document.getElementById('webgpu'); |
| const context = canvas.getContext('webgpu'); |
| const format = navigator.gpu.getPreferredCanvasFormat(); |
| context.configure({ |
| device: device, |
| format: format, |
| }); |
| |
| |
| |
| const vertexArray = new Float32Array([ |
| |
| -0.3, -0.5, 0.0, |
| 0.3, -0.5, 0.0, |
| 0.3, 0.5, 0.0, |
| |
| -0.3, -0.5, 0.0, |
| 0.3, 0.5, 0.0, |
| -0.3, 0.5, 0.0, |
| ]); |
| const vertexBuffer = device.createBuffer({ |
| size: vertexArray.byteLength, |
| usage: GPUBufferUsage.VERTEX | GPUBufferUsage.COPY_DST, |
| }); |
| device.queue.writeBuffer(vertexBuffer, 0, vertexArray); |
| |
| |
| |
| const pipeline = device.createRenderPipeline({ |
| layout: 'auto', |
| vertex: { |
| module: device.createShaderModule({ code: vertex }), |
| entryPoint: "main", |
| buffers: [ |
| { |
| arrayStride: 3 * 4, |
| attributes: [{ |
| shaderLocation: 0, |
| format: "float32x3", |
| offset: 0 |
| }] |
| } |
| ] |
| }, |
| fragment: { |
| module: device.createShaderModule({ code: fragment }), |
| entryPoint: "main", |
| targets: [{ |
| format: format |
| }] |
| }, |
| primitive: { |
| topology: "triangle-list", |
| } |
| }); |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| const modelMatrixBuffer = device.createBuffer({ |
| size: 16*4, |
| usage: GPUBufferUsage.UNIFORM | GPUBufferUsage.COPY_DST |
| }); |
| |
| |
| const bindGroup = device.createBindGroup({ |
| layout: pipeline.getBindGroupLayout(0), |
| entries: [ |
| { |
| |
| binding: 0, |
| resource: { buffer: modelMatrixBuffer } |
| } |
| ] |
| }); |
| |
| |
| let angle = 0.0; |
| function render() { |
| angle += 0.05; |
| const modelMatrix = glMatrix.mat4.create(); |
| |
| glMatrix.mat4.translate(modelMatrix, modelMatrix,[0,0,0.5]); |
| glMatrix.mat4.rotateY(modelMatrix, modelMatrix,angle); |
| device.queue.writeBuffer(modelMatrixBuffer, 0, modelMatrix) |
| |
| |
| const commandEncoder = device.createCommandEncoder(); |
| |
| const renderPass = commandEncoder.beginRenderPass({ |
| colorAttachments: [{ |
| view: context.getCurrentTexture().createView(), |
| storeOp: 'store', |
| |
| loadOp: 'clear', |
| }] |
| }); |
| renderPass.setPipeline(pipeline); |
| |
| renderPass.setVertexBuffer(0, vertexBuffer); |
| |
| renderPass.setBindGroup(0, bindGroup); |
| renderPass.draw(6); |
| renderPass.end(); |
| const commandBuffer = commandEncoder.finish(); |
| device.queue.submit([commandBuffer]); |
| |
| requestAnimationFrame(render); |
| } |
| render() |
| </script> |
| </body> |
| |
| </html> |
| |
| const vertex = ` |
| @group(0) @binding(0) var<uniform> modelMatrix:mat4x4<f32>; |
| @vertex |
| fn main(@location(0) pos: vec3<f32>) -> @builtin(position) vec4<f32> { |
| return modelMatrix * vec4<f32>(pos,1.0); |
| } |
| ` |
| |
| |
| const fragment = ` |
| @fragment |
| fn main() -> @location(0) vec4<f32> { |
| return vec4<f32>(1.0, 0.0, 0.0, 1.0); |
| } |
| ` |
| |
| export { vertex, fragment } |
| |
| |
| |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <canvas id="webgpu" width="500" height="500"></canvas> |
| <script type="module"> |
| |
| import { vertex, fragment } from './shader.js' |
| |
| |
| const adapter = await navigator.gpu.requestAdapter(); |
| const device = await adapter.requestDevice(); |
| const canvas = document.getElementById('webgpu'); |
| const context = canvas.getContext('webgpu'); |
| const format = navigator.gpu.getPreferredCanvasFormat(); |
| context.configure({ |
| device: device, |
| format: format, |
| }); |
| |
| |
| |
| const vertexArray = new Float32Array([ |
| 0.0, 0.0, 0.0, |
| 1.0, 0.0, 0.0, |
| 0.0, 1.0, 0.0, |
| ]); |
| const vertexBuffer = device.createBuffer({ |
| size: vertexArray.byteLength, |
| usage: GPUBufferUsage.VERTEX | GPUBufferUsage.COPY_DST, |
| }); |
| device.queue.writeBuffer(vertexBuffer, 0, vertexArray); |
| |
| |
| |
| const pipeline = device.createRenderPipeline({ |
| layout: 'auto', |
| vertex: { |
| module: device.createShaderModule({ code: vertex }), |
| entryPoint: "main", |
| buffers: [ |
| { |
| arrayStride: 3 * 4, |
| attributes: [{ |
| shaderLocation: 0, |
| format: "float32x3", |
| offset: 0 |
| }] |
| } |
| ] |
| }, |
| fragment: { |
| module: device.createShaderModule({ code: fragment }), |
| entryPoint: "main", |
| targets: [{ |
| format: format |
| }] |
| }, |
| primitive: { |
| topology: "triangle-list", |
| } |
| }); |
| |
| |
| const commandEncoder = device.createCommandEncoder(); |
| |
| const renderPass = commandEncoder.beginRenderPass({ |
| colorAttachments: [{ |
| view: context.getCurrentTexture().createView(), |
| storeOp: 'store', |
| loadOp: 'clear', |
| }] |
| }); |
| renderPass.setPipeline(pipeline); |
| |
| renderPass.setVertexBuffer(0, vertexBuffer); |
| renderPass.draw(3); |
| renderPass.end(); |
| const commandBuffer = commandEncoder.finish(); |
| device.queue.submit([commandBuffer]); |
| </script> |
| </body> |
| |
| </html> |
| |
| const vertex = ` |
| struct Out{ |
| @builtin(position) position:vec4<f32>, |
| // 位置变量vPosition表示顶点位置坐标插值后的坐标 |
| // 通过location标记改变量,location的参数可以是0、1、2等 |
| // vPosition用来表示每个片元的xyz坐标 |
| @location(0) vPosition:vec3<f32>, |
| } |
| |
| @vertex |
| fn main(@location(0) pos: vec3<f32>) -> Out { |
| var out:Out;//通过结构体声明一个变量 |
| out.position = vec4<f32>(pos,1.0); |
| out.vPosition = pos;//插值计算,生成的每个片元对应的xyz坐标 |
| return out; |
| } |
| `; |
| |
| |
| const fragment = ` |
| @fragment |
| // main参数通过@location(0)声明一个变量,和顶点着色器中vPosition变量关联起来 |
| fn main(@location(0) vPosition:vec3<f32>) -> @location(0) vec4<f32> { |
| // 根据x坐标设置片元颜色 |
| if(vPosition.x<0.5){ |
| return vec4<f32>(1.0, 0.0, 0.0, 1.0); |
| }else{ |
| return vec4<f32>(0.0, 1.0, 0.0, 1.0); |
| } |
| } |
| `; |
| |
| export { vertex, fragment }; |
| |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <canvas id="webgpu" width="500" height="500"></canvas> |
| <script type="module"> |
| |
| import { vertex, fragment } from './shader.js' |
| |
| |
| const adapter = await navigator.gpu.requestAdapter(); |
| const device = await adapter.requestDevice(); |
| const canvas = document.getElementById('webgpu'); |
| const context = canvas.getContext('webgpu'); |
| const format = navigator.gpu.getPreferredCanvasFormat(); |
| context.configure({ |
| device: device, |
| format: format, |
| }); |
| |
| |
| |
| const vertexArray = new Float32Array([ |
| 0.0, 0.0, 0.0, |
| 1.0, 0.0, 0.0, |
| 0.0, 1.0, 0.0, |
| ]); |
| const vertexBuffer = device.createBuffer({ |
| size: vertexArray.byteLength, |
| usage: GPUBufferUsage.VERTEX | GPUBufferUsage.COPY_DST, |
| }); |
| device.queue.writeBuffer(vertexBuffer, 0, vertexArray); |
| |
| |
| |
| const pipeline = device.createRenderPipeline({ |
| layout: 'auto', |
| vertex: { |
| module: device.createShaderModule({ code: vertex }), |
| entryPoint: "main", |
| buffers: [ |
| { |
| arrayStride: 3 * 4, |
| attributes: [{ |
| shaderLocation: 0, |
| format: "float32x3", |
| offset: 0 |
| }] |
| } |
| ] |
| }, |
| fragment: { |
| module: device.createShaderModule({ code: fragment }), |
| entryPoint: "main", |
| targets: [{ |
| format: format |
| }] |
| }, |
| primitive: { |
| topology: "triangle-list", |
| } |
| }); |
| |
| |
| const commandEncoder = device.createCommandEncoder(); |
| |
| const renderPass = commandEncoder.beginRenderPass({ |
| colorAttachments: [{ |
| view: context.getCurrentTexture().createView(), |
| storeOp: 'store', |
| loadOp: 'clear', |
| }] |
| }); |
| renderPass.setPipeline(pipeline); |
| |
| renderPass.setVertexBuffer(0, vertexBuffer); |
| renderPass.draw(3); |
| renderPass.end(); |
| const commandBuffer = commandEncoder.finish(); |
| device.queue.submit([commandBuffer]); |
| </script> |
| </body> |
| |
| </html> |
| |
| const vertex = ` |
| struct Out{ |
| @builtin(position) position:vec4<f32>, |
| } |
| @vertex |
| fn main(@location(0) pos: vec3<f32>) -> Out { |
| var out:Out; |
| out.position = vec4<f32>(pos,1.0); |
| return out; |
| } |
| ` |
| |
| |
| |
| const fragment = ` |
| @fragment |
| fn main() -> @location(0) vec4<f32> { |
| return vec4<f32>(1.0, 0.0, 0.0, 1.0); |
| } |
| ` |
| |
| export { vertex, fragment } |
| |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <meta http-equiv="X-UA-Compatible" content="IE=edge"> |
| <meta name="viewport" content="width=device-width, initial-scale=1.0"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <canvas id="webgpu" width="500" height="500"></canvas> |
| <script type="module"> |
| |
| import { vertex, fragment } from './shader.js' |
| |
| |
| const adapter = await navigator.gpu.requestAdapter(); |
| const device = await adapter.requestDevice(); |
| const canvas = document.getElementById('webgpu'); |
| const context = canvas.getContext('webgpu'); |
| const format = navigator.gpu.getPreferredCanvasFormat(); |
| context.configure({ |
| device: device, |
| format: format, |
| }); |
| |
| |
| |
| |
| |
| const vertexArray = new Float32Array([ |
| 1.0, 0.0, 0.0, |
| 0.0, 1.0, 0.0, |
| 0.0, 0.0, 1.0, |
| ]); |
| const vertexBuffer = device.createBuffer({ |
| size: vertexArray.byteLength, |
| usage: GPUBufferUsage.VERTEX | GPUBufferUsage.COPY_DST, |
| }); |
| device.queue.writeBuffer(vertexBuffer, 0, vertexArray); |
| |
| |
| |
| const pipeline = device.createRenderPipeline({ |
| layout: 'auto', |
| vertex: { |
| module: device.createShaderModule({ code: vertex }), |
| entryPoint: "main", |
| buffers: [ |
| { |
| arrayStride: 3 * 4, |
| attributes: [{ |
| shaderLocation: 0, |
| format: "float32x3", |
| offset: 0 |
| }] |
| } |
| ] |
| }, |
| fragment: { |
| module: device.createShaderModule({ code: fragment }), |
| entryPoint: "main", |
| targets: [{ |
| format: format |
| }] |
| }, |
| primitive: { |
| topology: "triangle-list", |
| } |
| }); |
| |
| |
| const commandEncoder = device.createCommandEncoder(); |
| |
| const renderPass = commandEncoder.beginRenderPass({ |
| colorAttachments: [{ |
| view: context.getCurrentTexture().createView(), |
| storeOp: 'store', |
| loadOp: 'clear', |
| }] |
| }); |
| renderPass.setPipeline(pipeline); |
| |
| renderPass.setVertexBuffer(0, vertexBuffer); |
| renderPass.draw(3); |
| renderPass.end(); |
| const commandBuffer = commandEncoder.finish(); |
| device.queue.submit([commandBuffer]); |
| </script> |
| </body> |
| |
| </html> |
| |
| const vertex = ` |
| @vertex |
| fn main(@location(0) pos: vec3<f32>) -> @builtin(position) vec4<f32> { |
| return vec4<f32>(pos,1.0); |
| } |
| ` |
| |
| |
| const fragment = ` |
| @fragment |
| fn main(@builtin(position) fragCoord : vec4<f32>) -> @location(0) vec4<f32> { |
| //片元深度值 |
| var z = fragCoord.z; |
| // if(z < 0.5){ |
| // // 片元深度值小于0.5,片元设置为红色 |
| // return vec4<f32>(1.0, 0.0, 0.0, 1.0); |
| // }else{ |
| // // 片元深度值不小于250,片元设置为绿色 |
| // return vec4<f32>(0.0, 1.0, 0.0, 1.0); |
| // } |
| // 可视化片元深度 |
| // return vec4<f32>(z, 1.0, 0.0, 1.0); |
| return vec4<f32>(z,0.0, 1.0-z, 1.0); |
| } |
| ` |
| |
| export { |
| vertex, |
| fragment |
| } |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <canvas id="webgpu" width="500" height="500"></canvas> |
| <script type="module"> |
| |
| import { vertex, fragment } from './shader.js' |
| |
| |
| const adapter = await navigator.gpu.requestAdapter(); |
| const device = await adapter.requestDevice(); |
| const canvas = document.getElementById('webgpu'); |
| const context = canvas.getContext('webgpu'); |
| const format = navigator.gpu.getPreferredCanvasFormat(); |
| context.configure({ |
| device: device, |
| format: format, |
| }); |
| |
| |
| |
| const vertexArray = new Float32Array([ |
| 1.0, 0.0, 0.0, |
| 0.0, 1.0, 0.0, |
| 0.0, 0.0, 1.0, |
| ]); |
| const vertexBuffer = device.createBuffer({ |
| size: vertexArray.byteLength, |
| usage: GPUBufferUsage.VERTEX | GPUBufferUsage.COPY_DST, |
| }); |
| device.queue.writeBuffer(vertexBuffer, 0, vertexArray); |
| |
| |
| |
| const pipeline = device.createRenderPipeline({ |
| layout: 'auto', |
| vertex: { |
| module: device.createShaderModule({ code: vertex }), |
| entryPoint: "main", |
| buffers: [ |
| { |
| arrayStride: 3 * 4, |
| attributes: [{ |
| shaderLocation: 0, |
| format: "float32x3", |
| offset: 0 |
| }] |
| } |
| ] |
| }, |
| fragment: { |
| module: device.createShaderModule({ code: fragment }), |
| entryPoint: "main", |
| targets: [{ |
| format: format |
| }] |
| }, |
| primitive: { |
| topology: "triangle-list", |
| } |
| }); |
| |
| |
| const commandEncoder = device.createCommandEncoder(); |
| |
| const renderPass = commandEncoder.beginRenderPass({ |
| colorAttachments: [{ |
| view: context.getCurrentTexture().createView(), |
| storeOp: 'store', |
| loadOp: 'clear', |
| }] |
| }); |
| renderPass.setPipeline(pipeline); |
| |
| renderPass.setVertexBuffer(0, vertexBuffer); |
| renderPass.draw(3); |
| renderPass.end(); |
| const commandBuffer = commandEncoder.finish(); |
| device.queue.submit([commandBuffer]); |
| </script> |
| </body> |
| |
| </html> |
| |
| const vertex = ` |
| struct Out{ |
| @builtin(position) position:vec4<f32>, |
| @location(0) vPosition:vec3<f32> |
| } |
| @vertex |
| fn main(@location(0) pos: vec3<f32>) -> Out{ |
| var out:Out; |
| out.position = vec4<f32>(pos,1.0); |
| out.vPosition = pos;////插值计算,生成的每个片元对应的xyz坐标 |
| return out; |
| } |
| ` |
| |
| |
| |
| const fragment = ` |
| @fragment |
| fn main(@location(0) vPosition:vec3<f32>) -> @location(0) vec4<f32> { |
| // if(vPosition.y<0.5){ |
| // return vec4<f32>(1.0, 0.0, 0.0, 1.0); |
| // }else{ |
| // return vec4<f32>(0.0, 1.0, 0.0, 1.0); |
| // } |
| return vec4<f32>(vPosition.x, 0.0, 1.0-vPosition.x, 1.0); |
| |
| } |
| ` |
| |
| export { vertex, fragment } |
| |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <script type="module"> |
| import * as glMatrix from './gl-matrix-master/dist/esm/index.js' |
| |
| |
| const modelMatrix = glMatrix.mat4.create(); |
| |
| glMatrix.mat4.scale(modelMatrix, modelMatrix, [10, 1, 1]); |
| |
| glMatrix.mat4.translate(modelMatrix, modelMatrix, [2, 0, 0]); |
| console.log('modelMatrix', modelMatrix); |
| |
| const p1 = glMatrix.vec3.fromValues(2, 0, 0); |
| const p2 = glMatrix.vec3.create(); |
| console.log('p2',p2); |
| |
| glMatrix.vec3.transformMat4(p2, p1, modelMatrix); |
| console.log('p2', p2); |
| </script> |
| </body> |
| |
| </html> |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <script type="module"> |
| import * as glMatrix from './gl-matrix-master/dist/esm/index.js' |
| |
| |
| |
| |
| const modelMatrix = glMatrix.mat4.create(); |
| |
| glMatrix.mat4.scale(modelMatrix, modelMatrix, [10, 1, 1]); |
| |
| glMatrix.mat4.translate(modelMatrix, modelMatrix, [2, 0, 0]); |
| console.log('modelMatrix', modelMatrix); |
| </script> |
| </body> |
| |
| </html> |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <script type="module"> |
| |
| import * as glMatrix from './gl-matrix-master/dist/esm/index.js' |
| console.log('glMatrix.mat4', glMatrix.mat4); |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| const mat4T = glMatrix.mat4.fromValues(1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 1, 2, 3, 1); |
| |
| |
| |
| |
| |
| |
| |
| const mat4S = glMatrix.mat4.fromValues(1, 0, 0, 0, 0, 2, 0, 0, 0, 0, 3, 0, 0, 0, 0, 1); |
| |
| |
| console.log('mat4T', mat4T); |
| console.log('mat4S', mat4S); |
| |
| |
| </script> |
| </body> |
| |
| </html> |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <script type="module"> |
| import * as glMatrix from './gl-matrix-master/dist/esm/index.js' |
| console.log('glMatrix', glMatrix); |
| |
| |
| const mat4 = glMatrix.mat4.create(); |
| console.log('mat4',mat4); |
| |
| |
| const mat4T = glMatrix.mat4.create(); |
| glMatrix.mat4.translate(mat4T,mat4,[2,0,0]); |
| |
| const mat4S = glMatrix.mat4.create(); |
| glMatrix.mat4.scale(mat4S,mat4,[10,1,1]); |
| |
| console.log('mat4T',mat4T); |
| console.log('mat4S',mat4S); |
| |
| |
| |
| const mat4X = glMatrix.mat4.create(); |
| glMatrix.mat4.rotateX(mat4X,mat4,Math.PI/4); |
| console.log('mat4X',mat4X); |
| |
| |
| const mat4Y = glMatrix.mat4.create(); |
| glMatrix.mat4.rotateY(mat4Y,mat4,Math.PI/4); |
| console.log('mat4Y',mat4Y); |
| |
| |
| const mat4Z = glMatrix.mat4.create(); |
| glMatrix.mat4.rotateZ(mat4Z,mat4,Math.PI/4); |
| console.log('mat4Z',mat4Z); |
| |
| |
| |
| |
| </script> |
| </body> |
| |
| </html> |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <script type="module"> |
| import * as glMatrix from './gl-matrix-master/dist/esm/index.js' |
| |
| |
| const mat4 = glMatrix.mat4.create(); |
| |
| |
| const mat4T = glMatrix.mat4.create(); |
| glMatrix.mat4.translate(mat4T,mat4,[2,0,0]); |
| |
| const mat4S = glMatrix.mat4.create(); |
| glMatrix.mat4.scale(mat4S,mat4,[10,1,1]); |
| |
| |
| |
| const modelMatrix = glMatrix.mat4.create(); |
| glMatrix.mat4.multiply(modelMatrix,modelMatrix,mat4S); |
| glMatrix.mat4.multiply(modelMatrix,modelMatrix,mat4T); |
| console.log('modelMatrix',modelMatrix); |
| </script> |
| </body> |
| |
| </html> |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <meta http-equiv="X-UA-Compatible" content="IE=edge"> |
| <meta name="viewport" content="width=device-width, initial-scale=1.0"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <canvas id="webgpu" width="500" height="500"></canvas> |
| <script type="module"> |
| |
| import { vertex, fragment } from './shader.js' |
| |
| |
| const adapter = await navigator.gpu.requestAdapter(); |
| const device = await adapter.requestDevice(); |
| const canvas = document.getElementById('webgpu'); |
| const context = canvas.getContext('webgpu'); |
| const format = navigator.gpu.getPreferredCanvasFormat(); |
| context.configure({ |
| device: device, |
| format: format, |
| }); |
| |
| |
| |
| const vertexArray = new Float32Array([ |
| |
| 0.0, 0.0, 0.0, |
| 1.0, 0.0, 0.0, |
| 0.0, 1.0, 0.0, |
| ]); |
| const vertexBuffer = device.createBuffer({ |
| size: vertexArray.byteLength, |
| usage: GPUBufferUsage.VERTEX | GPUBufferUsage.COPY_DST, |
| }); |
| device.queue.writeBuffer(vertexBuffer, 0, vertexArray); |
| |
| |
| |
| const pipeline = device.createRenderPipeline({ |
| layout: 'auto', |
| vertex: { |
| module: device.createShaderModule({ code: vertex }), |
| entryPoint: "main", |
| buffers: [ |
| { |
| arrayStride: 3 * 4, |
| attributes: [{ |
| shaderLocation: 0, |
| format: "float32x3", |
| offset: 0 |
| }] |
| } |
| ] |
| }, |
| fragment: { |
| module: device.createShaderModule({ code: fragment }), |
| entryPoint: "main", |
| targets: [{ |
| format: format |
| }] |
| }, |
| primitive: { |
| topology: "triangle-list", |
| |
| } |
| }); |
| |
| |
| const commandEncoder = device.createCommandEncoder(); |
| |
| const renderPass = commandEncoder.beginRenderPass({ |
| colorAttachments: [{ |
| view: context.getCurrentTexture().createView(), |
| storeOp: 'store', |
| |
| loadOp: 'clear', |
| }] |
| }); |
| renderPass.setPipeline(pipeline); |
| |
| renderPass.setVertexBuffer(0, vertexBuffer); |
| renderPass.draw(3); |
| renderPass.end(); |
| const commandBuffer = commandEncoder.finish(); |
| device.queue.submit([commandBuffer]); |
| </script> |
| </body> |
| |
| </html> |
| |
| const vertex = ` |
| @vertex |
| fn main(@location(0) pos: vec3<f32>) -> @builtin(position) vec4<f32> { |
| // 创建一个平移矩阵(沿着x、y轴分别平移-1、-1) |
| var T:mat4x4<f32> = mat4x4<f32>(1.0,0.0,0.0,0.0, 0.0,1.0,0.0,0.0, 0.0,0.0,1.0,0.0, -1.0,-1.0,0.0,1.0); |
| // 创建一个缩放矩阵(沿着x、y分别缩放0.5倍) |
| var S = mat4x4<f32>(0.5,0.0,0.0,0.0, 0.0,0.5,0.0,0.0, 0.0,0.0,1.0,0.0, 0.0,0.0,0.0,1.0); |
| return S * T * vec4<f32>(pos,1.0);// 先平移、后缩放(矩阵顺序从右往左) |
| // return T * S * vec4<f32>(pos,1.0);// 先缩放、后平移(矩阵顺序从右往左) |
| } |
| ` |
| |
| |
| const fragment = ` |
| @fragment |
| fn main() -> @location(0) vec4<f32> { |
| return vec4<f32>(1.0, 0.0, 0.0, 1.0); |
| } |
| ` |
| |
| export { |
| vertex, |
| fragment |
| } |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <meta http-equiv="X-UA-Compatible" content="IE=edge"> |
| <meta name="viewport" content="width=device-width, initial-scale=1.0"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <canvas id="webgpu" width="500" height="500"></canvas> |
| <script type="module"> |
| |
| import { vertex, fragment } from './shader.js' |
| |
| |
| const adapter = await navigator.gpu.requestAdapter(); |
| const device = await adapter.requestDevice(); |
| const canvas = document.getElementById('webgpu'); |
| const context = canvas.getContext('webgpu'); |
| const format = navigator.gpu.getPreferredCanvasFormat(); |
| context.configure({ |
| device: device, |
| format: format, |
| }); |
| |
| |
| |
| const vertexArray = new Float32Array([ |
| |
| 0.0, 0.0, 0.0, |
| 1.0, 0.0, 0.0, |
| 0.0, 1.0, 0.0, |
| ]); |
| const vertexBuffer = device.createBuffer({ |
| size: vertexArray.byteLength, |
| usage: GPUBufferUsage.VERTEX | GPUBufferUsage.COPY_DST, |
| }); |
| device.queue.writeBuffer(vertexBuffer, 0, vertexArray); |
| |
| |
| |
| const pipeline = device.createRenderPipeline({ |
| layout: 'auto', |
| vertex: { |
| module: device.createShaderModule({ code: vertex }), |
| entryPoint: "main", |
| buffers: [ |
| { |
| arrayStride: 3 * 4, |
| attributes: [{ |
| shaderLocation: 0, |
| format: "float32x3", |
| offset: 0 |
| }] |
| } |
| ] |
| }, |
| fragment: { |
| module: device.createShaderModule({ code: fragment }), |
| entryPoint: "main", |
| targets: [{ |
| format: format |
| }] |
| }, |
| primitive: { |
| topology: "triangle-list", |
| |
| } |
| }); |
| |
| |
| const commandEncoder = device.createCommandEncoder(); |
| |
| const renderPass = commandEncoder.beginRenderPass({ |
| colorAttachments: [{ |
| view: context.getCurrentTexture().createView(), |
| storeOp: 'store', |
| |
| loadOp: 'clear', |
| }] |
| }); |
| renderPass.setPipeline(pipeline); |
| |
| renderPass.setVertexBuffer(0, vertexBuffer); |
| renderPass.draw(3); |
| renderPass.end(); |
| const commandBuffer = commandEncoder.finish(); |
| device.queue.submit([commandBuffer]); |
| </script> |
| </body> |
| |
| </html> |
| |
| const vertex = ` |
| @vertex |
| fn main(@location(0) pos: vec3<f32>) -> @builtin(position) vec4<f32> { |
| // 创建一个平移矩阵(沿着x、y轴分别平移-1、-1) |
| //1 0 0 -1 |
| //0 1 0 -1 |
| //0 0 1 0 |
| //0 0 0 1 |
| // 矩阵元素一列一列输入mat4x4<f32>() |
| var T:mat4x4<f32> = mat4x4<f32>(1.0,0.0,0.0,0.0, 0.0,1.0,0.0,0.0, 0.0,0.0,1.0,0.0, -1.0,-1.0,0.0,1.0); |
| return T * vec4<f32>(pos,1.0);//平移矩阵对顶点平移变换 |
| } |
| ` |
| |
| |
| const fragment = ` |
| @fragment |
| fn main() -> @location(0) vec4<f32> { |
| return vec4<f32>(1.0, 0.0, 0.0, 1.0); |
| } |
| ` |
| |
| export { |
| vertex, |
| fragment |
| } |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <meta http-equiv="X-UA-Compatible" content="IE=edge"> |
| <meta name="viewport" content="width=device-width, initial-scale=1.0"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <canvas id="webgpu" width="500" height="500"></canvas> |
| <script type="module"> |
| |
| import { vertex, fragment } from './shader.js' |
| |
| |
| const adapter = await navigator.gpu.requestAdapter(); |
| const device = await adapter.requestDevice(); |
| const canvas = document.getElementById('webgpu'); |
| const context = canvas.getContext('webgpu'); |
| const format = navigator.gpu.getPreferredCanvasFormat(); |
| context.configure({ |
| device: device, |
| format: format, |
| }); |
| |
| |
| |
| const vertexArray = new Float32Array([ |
| |
| 0.0, 0.0, 0.0, |
| 1.0, 0.0, 0.0, |
| 0.0, 1.0, 0.0, |
| ]); |
| const vertexBuffer = device.createBuffer({ |
| size: vertexArray.byteLength, |
| usage: GPUBufferUsage.VERTEX | GPUBufferUsage.COPY_DST, |
| }); |
| device.queue.writeBuffer(vertexBuffer, 0, vertexArray); |
| |
| |
| |
| const pipeline = device.createRenderPipeline({ |
| layout: 'auto', |
| vertex: { |
| module: device.createShaderModule({ code: vertex }), |
| entryPoint: "main", |
| buffers: [ |
| { |
| arrayStride: 3 * 4, |
| attributes: [{ |
| shaderLocation: 0, |
| format: "float32x3", |
| offset: 0 |
| }] |
| } |
| ] |
| }, |
| fragment: { |
| module: device.createShaderModule({ code: fragment }), |
| entryPoint: "main", |
| targets: [{ |
| format: format |
| }] |
| }, |
| primitive: { |
| topology: "triangle-list", |
| |
| } |
| }); |
| |
| |
| const commandEncoder = device.createCommandEncoder(); |
| |
| const renderPass = commandEncoder.beginRenderPass({ |
| colorAttachments: [{ |
| view: context.getCurrentTexture().createView(), |
| storeOp: 'store', |
| |
| loadOp: 'clear', |
| }] |
| }); |
| renderPass.setPipeline(pipeline); |
| |
| renderPass.setVertexBuffer(0, vertexBuffer); |
| renderPass.draw(3); |
| renderPass.end(); |
| const commandBuffer = commandEncoder.finish(); |
| device.queue.submit([commandBuffer]); |
| </script> |
| </body> |
| |
| </html> |
| |
| const vertex = ` |
| @vertex |
| fn main(@location(0) pos: vec3<f32>) -> @builtin(position) vec4<f32> { |
| // 创建一个平移矩阵(沿着x、y轴分别平移-1、-1) |
| var T:mat4x4<f32> = mat4x4<f32>(1.0,0.0,0.0,0.0, 0.0,1.0,0.0,0.0, 0.0,0.0,1.0,0.0, -1.0,-1.0,0.0,1.0); |
| // 创建一个缩放矩阵(沿着x、y分别缩放0.5倍) |
| var S = mat4x4<f32>(0.5,0.0,0.0,0.0, 0.0,0.5,0.0,0.0, 0.0,0.0,1.0,0.0, 0.0,0.0,0.0,1.0); |
| // return S * T * vec4<f32>(pos,1.0);// 先平移、后缩放(矩阵顺序从右往左) |
| return T * S * vec4<f32>(pos,1.0);// 先缩放、后平移(矩阵顺序从右往左) |
| } |
| ` |
| |
| |
| const fragment = ` |
| @fragment |
| fn main() -> @location(0) vec4<f32> { |
| return vec4<f32>(1.0, 0.0, 0.0, 1.0); |
| } |
| ` |
| |
| export { |
| vertex, |
| fragment |
| } |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <meta http-equiv="X-UA-Compatible" content="IE=edge"> |
| <meta name="viewport" content="width=device-width, initial-scale=1.0"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <canvas id="webgpu" width="500" height="500"></canvas> |
| <script type="module"> |
| |
| import { vertex, fragment } from './shader.js' |
| |
| |
| const adapter = await navigator.gpu.requestAdapter(); |
| const device = await adapter.requestDevice(); |
| const canvas = document.getElementById('webgpu'); |
| const context = canvas.getContext('webgpu'); |
| const format = navigator.gpu.getPreferredCanvasFormat(); |
| context.configure({ |
| device: device, |
| format: format, |
| }); |
| |
| |
| const vertexArray = new Float32Array([ |
| |
| 0.0, 0.0, 0.0, |
| 1.0, 0.0, 0.0, |
| 0.0, 1.0, 0.0, |
| ]); |
| const vertexBuffer = device.createBuffer({ |
| size: vertexArray.byteLength, |
| usage: GPUBufferUsage.VERTEX | GPUBufferUsage.COPY_DST, |
| }); |
| device.queue.writeBuffer(vertexBuffer, 0, vertexArray); |
| |
| |
| |
| const pipeline = device.createRenderPipeline({ |
| layout: 'auto', |
| vertex: { |
| module: device.createShaderModule({ code: vertex }), |
| entryPoint: "main", |
| buffers: [ |
| { |
| arrayStride: 3 * 4, |
| attributes: [{ |
| shaderLocation: 0, |
| format: "float32x3", |
| offset: 0 |
| }] |
| } |
| ] |
| }, |
| fragment: { |
| module: device.createShaderModule({ code: fragment }), |
| entryPoint: "main", |
| targets: [{ |
| format: format |
| }] |
| }, |
| primitive: { |
| topology: "triangle-list", |
| |
| } |
| }); |
| |
| |
| const commandEncoder = device.createCommandEncoder(); |
| |
| const renderPass = commandEncoder.beginRenderPass({ |
| colorAttachments: [{ |
| view: context.getCurrentTexture().createView(), |
| storeOp: 'store', |
| |
| loadOp: 'clear', |
| }] |
| }); |
| renderPass.setPipeline(pipeline); |
| |
| renderPass.setVertexBuffer(0, vertexBuffer); |
| renderPass.draw(3); |
| renderPass.end(); |
| const commandBuffer = commandEncoder.finish(); |
| device.queue.submit([commandBuffer]); |
| </script> |
| </body> |
| |
| </html> |
| |
| const vertex = ` |
| @vertex |
| fn main(@location(0) pos: vec3<f32>) -> @builtin(position) vec4<f32> { |
| // 创建一个缩放矩阵(沿着x、y分别缩放0.5倍) |
| //0.5 0 0 0 |
| //0 0.5 0 0 |
| //0 0 1 0 |
| //0 0 0 1 |
| // 矩阵元素一列一列输入mat4x4<f32>() |
| var S = mat4x4<f32>(0.5,0.0,0.0,0.0, 0.0,0.5,0.0,0.0, 0.0,0.0,1.0,0.0, 0.0,0.0,0.0,1.0); |
| return S * vec4<f32>(pos,1.0);//缩放矩阵对顶点缩放变换 |
| } |
| ` |
| |
| |
| const fragment = ` |
| @fragment |
| fn main() -> @location(0) vec4<f32> { |
| return vec4<f32>(1.0, 0.0, 0.0, 1.0); |
| } |
| ` |
| |
| export { vertex, fragment } |
| |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <meta http-equiv="X-UA-Compatible" content="IE=edge"> |
| <meta name="viewport" content="width=device-width, initial-scale=1.0"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <canvas id="webgpu" width="500" height="500"></canvas> |
| <script type="module"> |
| |
| import { vertex, fragment } from './shader.js' |
| |
| |
| const adapter = await navigator.gpu.requestAdapter(); |
| const device = await adapter.requestDevice(); |
| const canvas = document.getElementById('webgpu'); |
| const context = canvas.getContext('webgpu'); |
| const format = navigator.gpu.getPreferredCanvasFormat(); |
| context.configure({ |
| device: device, |
| format: format, |
| }); |
| |
| |
| |
| const vertexArray = new Float32Array([ |
| |
| 0.0, 0.0, 0.0, |
| 1.0, 0.0, 0.0, |
| 0.0, 1.0, 0.0, |
| ]); |
| const vertexBuffer = device.createBuffer({ |
| size: vertexArray.byteLength, |
| usage: GPUBufferUsage.VERTEX | GPUBufferUsage.COPY_DST, |
| }); |
| device.queue.writeBuffer(vertexBuffer, 0, vertexArray); |
| |
| |
| |
| const pipeline = device.createRenderPipeline({ |
| layout: 'auto', |
| vertex: { |
| module: device.createShaderModule({ code: vertex }), |
| entryPoint: "main", |
| buffers: [ |
| { |
| arrayStride: 3 * 4, |
| attributes: [{ |
| shaderLocation: 0, |
| format: "float32x3", |
| offset: 0 |
| }] |
| } |
| ] |
| }, |
| fragment: { |
| module: device.createShaderModule({ code: fragment }), |
| entryPoint: "main", |
| targets: [{ |
| format: format |
| }] |
| }, |
| primitive: { |
| topology: "triangle-list", |
| |
| } |
| }); |
| |
| |
| const t = 0.5; |
| const tArray = new Float32Array([t]); |
| |
| const tBuffer = device.createBuffer({ |
| size: tArray.byteLength, |
| usage: GPUBufferUsage.UNIFORM | GPUBufferUsage.COPY_DST |
| }); |
| |
| device.queue.writeBuffer(tBuffer, 0, tArray); |
| |
| |
| |
| const bindGroup = device.createBindGroup({ |
| |
| layout: pipeline.getBindGroupLayout(0), |
| |
| entries: [ |
| { |
| |
| binding: 0, |
| resource: { buffer: tBuffer } |
| } |
| ] |
| }); |
| |
| |
| const commandEncoder = device.createCommandEncoder(); |
| |
| const renderPass = commandEncoder.beginRenderPass({ |
| colorAttachments: [{ |
| view: context.getCurrentTexture().createView(), |
| storeOp: 'store', |
| |
| loadOp: 'clear', |
| }] |
| }); |
| renderPass.setPipeline(pipeline); |
| |
| renderPass.setVertexBuffer(0, vertexBuffer); |
| |
| renderPass.setBindGroup( 0, bindGroup ); |
| renderPass.draw(3); |
| renderPass.end(); |
| const commandBuffer = commandEncoder.finish(); |
| device.queue.submit([commandBuffer]); |
| </script> |
| </body> |
| |
| </html> |
| |
| const vertex = ` |
| @group(0) @binding(0) var<uniform> t:f32; |
| @vertex |
| fn main(@location(0) pos: vec3<f32>) -> @builtin(position) vec4<f32> { |
| // 创建一个缩放矩阵(沿着x、y分别缩放t倍) |
| //t 0 0 0 |
| //0 t 0 0 |
| //0 0 1 0 |
| //0 0 0 1 |
| // 矩阵元素一列一列输入mat4x4<f32>() |
| var S = mat4x4<f32>(t,0.0,0.0,0.0, 0.0,t,0.0,0.0, 0.0,0.0,1.0,0.0, 0.0,0.0,0.0,1.0); |
| return S * vec4<f32>(pos,1.0);//缩放矩阵对顶点缩放变换 |
| } |
| ` |
| |
| |
| const fragment = ` |
| @fragment |
| fn main() -> @location(0) vec4<f32> { |
| return vec4<f32>(1.0, 0.0, 0.0, 1.0); |
| } |
| ` |
| |
| export { vertex, fragment } |
| |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <meta http-equiv="X-UA-Compatible" content="IE=edge"> |
| <meta name="viewport" content="width=device-width, initial-scale=1.0"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <canvas id="webgpu" width="500" height="500"></canvas> |
| <script type="module"> |
| |
| import { vertex, fragment } from './shader.js' |
| |
| |
| const adapter = await navigator.gpu.requestAdapter(); |
| const device = await adapter.requestDevice(); |
| const canvas = document.getElementById('webgpu'); |
| const context = canvas.getContext('webgpu'); |
| const format = navigator.gpu.getPreferredCanvasFormat(); |
| context.configure({ |
| device: device, |
| format: format, |
| }); |
| |
| |
| |
| const vertexArray = new Float32Array([ |
| |
| 0.0, 0.0, 0.0, |
| 1.0, 0.0, 0.0, |
| 0.0, 1.0, 0.0, |
| ]); |
| const vertexBuffer = device.createBuffer({ |
| size: vertexArray.byteLength, |
| usage: GPUBufferUsage.VERTEX | GPUBufferUsage.COPY_DST, |
| }); |
| device.queue.writeBuffer(vertexBuffer, 0, vertexArray); |
| |
| |
| |
| const pipeline = device.createRenderPipeline({ |
| layout: 'auto', |
| vertex: { |
| module: device.createShaderModule({ code: vertex }), |
| entryPoint: "main", |
| buffers: [ |
| { |
| arrayStride: 3 * 4, |
| attributes: [{ |
| shaderLocation: 0, |
| format: "float32x3", |
| offset: 0 |
| }] |
| } |
| ] |
| }, |
| fragment: { |
| module: device.createShaderModule({ code: fragment }), |
| entryPoint: "main", |
| targets: [{ |
| format: format |
| }] |
| }, |
| primitive: { |
| topology: "triangle-list", |
| |
| } |
| }); |
| |
| |
| |
| |
| |
| |
| |
| |
| const mat4Array = new Float32Array([0.5, 0.0, 0.0, 0.0, 0.0, 0.5, 0.0, 0.0, 0.0, 0.0, 1.0, 0.0, 0.0, 0.0, 0.0, 1.0]); |
| |
| const mat4Buffer = device.createBuffer({ |
| size: mat4Array.byteLength, |
| usage: GPUBufferUsage.UNIFORM | GPUBufferUsage.COPY_DST |
| }); |
| |
| device.queue.writeBuffer(mat4Buffer, 0, mat4Array); |
| |
| |
| const colorArray = new Float32Array([0.0,1.0,0.0]); |
| |
| const colorBuffer = device.createBuffer({ |
| size: colorArray.byteLength, |
| usage: GPUBufferUsage.UNIFORM | GPUBufferUsage.COPY_DST |
| }); |
| |
| device.queue.writeBuffer(colorBuffer, 0, colorArray); |
| |
| |
| |
| |
| const bindGroup = device.createBindGroup({ |
| |
| layout: pipeline.getBindGroupLayout(0), |
| |
| entries: [ |
| { |
| |
| binding: 0, |
| resource: { buffer: mat4Buffer } |
| }, |
| { |
| |
| binding: 1, |
| resource: { buffer: colorBuffer } |
| } |
| ] |
| }); |
| |
| |
| const commandEncoder = device.createCommandEncoder(); |
| |
| const renderPass = commandEncoder.beginRenderPass({ |
| colorAttachments: [{ |
| view: context.getCurrentTexture().createView(), |
| storeOp: 'store', |
| loadOp: 'clear', |
| }] |
| }); |
| renderPass.setPipeline(pipeline); |
| |
| renderPass.setVertexBuffer(0, vertexBuffer); |
| |
| renderPass.setBindGroup(0, bindGroup); |
| renderPass.draw(3); |
| renderPass.end(); |
| const commandBuffer = commandEncoder.finish(); |
| device.queue.submit([commandBuffer]); |
| </script> |
| </body> |
| |
| </html> |
| |
| const vertex = ` |
| // uniform关键字辅助var声明一个4x4矩阵变量 |
| //@group(0)的参数0对应webgpu代码.getBindGroupLayout(0)参数0 |
| //@binding(0)的参数对应webgpu代码.binding的值,保持一致,比如都是0 |
| @group(0) @binding(0) var<uniform> S:mat4x4<f32>; |
| @vertex |
| fn main(@location(0) pos: vec3<f32>) -> @builtin(position) vec4<f32> { |
| return S * vec4<f32>(pos,1.0);//缩放矩阵对顶点缩放变换 |
| } |
| ` |
| |
| |
| const fragment = ` |
| // uniform关键字辅助var声明一个三维向量变量color表示片元颜色 |
| //@binding(1)的参数对应webgpu代码.binding的值,保持一致,比如都是1 |
| @group(0) @binding(1) var<uniform> color:vec3<f32>; |
| @fragment |
| fn main() -> @location(0) vec4<f32> { |
| // return vec4<f32>(1.0, 0.0, 0.0, 1.0); |
| return vec4<f32>(color, 1.0); |
| } |
| ` |
| |
| export { vertex, fragment } |
| |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <meta http-equiv="X-UA-Compatible" content="IE=edge"> |
| <meta name="viewport" content="width=device-width, initial-scale=1.0"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <canvas id="webgpu" width="500" height="500"></canvas> |
| <script type="module"> |
| |
| import { vertex, fragment } from './shader.js' |
| |
| |
| const adapter = await navigator.gpu.requestAdapter(); |
| const device = await adapter.requestDevice(); |
| const canvas = document.getElementById('webgpu'); |
| const context = canvas.getContext('webgpu'); |
| const format = navigator.gpu.getPreferredCanvasFormat(); |
| context.configure({ |
| device: device, |
| format: format, |
| }); |
| |
| |
| |
| const vertexArray = new Float32Array([ |
| |
| 0.0, 0.0, 0.0, |
| 1.0, 0.0, 0.0, |
| 0.0, 1.0, 0.0, |
| ]); |
| const vertexBuffer = device.createBuffer({ |
| size: vertexArray.byteLength, |
| usage: GPUBufferUsage.VERTEX | GPUBufferUsage.COPY_DST, |
| }); |
| device.queue.writeBuffer(vertexBuffer, 0, vertexArray); |
| |
| |
| |
| const pipeline = device.createRenderPipeline({ |
| layout: 'auto', |
| vertex: { |
| module: device.createShaderModule({ code: vertex }), |
| entryPoint: "main", |
| buffers: [ |
| { |
| arrayStride: 3 * 4, |
| attributes: [{ |
| shaderLocation: 0, |
| format: "float32x3", |
| offset: 0 |
| }] |
| } |
| ] |
| }, |
| fragment: { |
| module: device.createShaderModule({ code: fragment }), |
| entryPoint: "main", |
| targets: [{ |
| format: format |
| }] |
| }, |
| primitive: { |
| topology: "triangle-list", |
| |
| } |
| }); |
| |
| |
| |
| |
| |
| |
| |
| |
| const mat4Array = new Float32Array([0.5, 0.0, 0.0, 0.0, 0.0, 0.5, 0.0, 0.0, 0.0, 0.0, 1.0, 0.0, 0.0, 0.0, 0.0, 1.0]); |
| |
| const mat4Buffer = device.createBuffer({ |
| size: mat4Array.byteLength, |
| usage: GPUBufferUsage.UNIFORM | GPUBufferUsage.COPY_DST |
| }); |
| |
| device.queue.writeBuffer(mat4Buffer, 0, mat4Array); |
| |
| |
| |
| const bindGroup = device.createBindGroup({ |
| |
| layout: pipeline.getBindGroupLayout(0), |
| |
| entries: [ |
| { |
| |
| binding: 0, |
| resource: { buffer: mat4Buffer } |
| } |
| ] |
| }); |
| |
| |
| const commandEncoder = device.createCommandEncoder(); |
| |
| const renderPass = commandEncoder.beginRenderPass({ |
| colorAttachments: [{ |
| view: context.getCurrentTexture().createView(), |
| storeOp: 'store', |
| |
| loadOp: 'clear', |
| }] |
| }); |
| renderPass.setPipeline(pipeline); |
| |
| renderPass.setVertexBuffer(0, vertexBuffer); |
| |
| renderPass.setBindGroup( 0, bindGroup ); |
| renderPass.draw(3); |
| renderPass.end(); |
| const commandBuffer = commandEncoder.finish(); |
| device.queue.submit([commandBuffer]); |
| </script> |
| </body> |
| |
| </html> |
| |
| const vertex = ` |
| // uniform关键字辅助var声明一个4x4矩阵变量 |
| //@group(0)的参数0对应webgpu代码.getBindGroupLayout(0)参数0 |
| //@binding(0)的参数对应webgpu代码.binding的值,保持一致,比如都是0 |
| @group(0) @binding(0) var<uniform> S:mat4x4<f32>; |
| @vertex |
| fn main(@location(0) pos: vec3<f32>) -> @builtin(position) vec4<f32> { |
| return S * vec4<f32>(pos,1.0);//缩放矩阵对顶点缩放变换 |
| } |
| ` |
| |
| |
| const fragment = ` |
| @fragment |
| fn main() -> @location(0) vec4<f32> { |
| return vec4<f32>(1.0, 0.0, 0.0, 1.0); |
| } |
| ` |
| |
| export { vertex, fragment } |
| |
| <!DOCTYPE html> |
| <html lang="en"> |
| |
| <head> |
| <meta charset="UTF-8"> |
| <meta http-equiv="X-UA-Compatible" content="IE=edge"> |
| <meta name="viewport" content="width=device-width, initial-scale=1.0"> |
| <title>Threejs中文网:http://www.webgl3d.cn/</title> |
| </head> |
| |
| <body> |
| |
| <canvas id="webgpu" width="500" height="500"></canvas> |
| <script type="module"> |
| |
| import { vertex, fragment } from './shader.js' |
| |
| |
| const adapter = await navigator.gpu.requestAdapter(); |
| const device = await adapter.requestDevice(); |
| const canvas = document.getElementById('webgpu'); |
| const context = canvas.getContext('webgpu'); |
| const format = navigator.gpu.getPreferredCanvasFormat(); |
| context.configure({ |
| device: device, |
| format: format, |
| }); |
| |
| |
| |
| const vertexArray = new Float32Array([ |
| |
| 0.0, 0.0, 0.0, |
| 1.0, 0.0, 0.0, |
| 0.0, 1.0, 0.0, |
| ]); |
| const vertexBuffer = device.createBuffer({ |
| size: vertexArray.byteLength, |
| usage: GPUBufferUsage.VERTEX | GPUBufferUsage.COPY_DST, |
| }); |
| device.queue.writeBuffer(vertexBuffer, 0, vertexArray); |
| |
| |
| |
| const pipeline = device.createRenderPipeline({ |
| layout: 'auto', |
| vertex: { |
| module: device.createShaderModule({ code: vertex }), |
| entryPoint: "main", |
| buffers: [ |
| { |
| arrayStride: 3 * 4, |
| attributes: [{ |
| shaderLocation: 0, |
| format: "float32x3", |
| offset: 0 |
| }] |
| } |
| ] |
| }, |
| fragment: { |
| module: device.createShaderModule({ code: fragment }), |
| entryPoint: "main", |
| targets: [{ |
| format: format |
| }] |
| }, |
| primitive: { |
| topology: "triangle-list", |
| |
| } |
| }); |
| |
| |
| |
| |
| |
| |
| |
| |
| const mat4Array = new Float32Array([0.5, 0.0, 0.0, 0.0, 0.0, 0.5, 0.0, 0.0, 0.0, 0.0, 1.0, 0.0, 0.0, 0.0, 0.0, 1.0]); |
| |
| const mat4Buffer = device.createBuffer({ |
| size: mat4Array.byteLength, |
| usage: GPUBufferUsage.UNIFORM | GPUBufferUsage.COPY_DST |
| }); |
| |
| device.queue.writeBuffer(mat4Buffer, 0, mat4Array); |
| |
| |
| const mat4Array2 = new Float32Array([1.0,0.0,0.0,0.0, 0.0,1.0,0.0,0.0, 0.0,0.0,1.0,0.0, -1.0,-1.0,0.0,1.0]); |
| |
| const mat4Buffer2 = device.createBuffer({ |
| size: mat4Array2.byteLength, |
| usage: GPUBufferUsage.UNIFORM | GPUBufferUsage.COPY_DST |
| }); |
| |
| device.queue.writeBuffer(mat4Buffer2, 0, mat4Array2); |
| |
| |
| |
| const bindGroup = device.createBindGroup({ |
| |
| layout: pipeline.getBindGroupLayout(0), |
| |
| entries: [ |
| { |
| |
| binding: 0, |
| resource: { buffer: mat4Buffer } |
| }, |
| { |
| |
| binding: 1, |
| resource: { buffer: mat4Buffer2 } |
| } |
| ] |
| }); |
| |
| |
| const commandEncoder = device.createCommandEncoder(); |
| |
| const renderPass = commandEncoder.beginRenderPass({ |
| colorAttachments: [{ |
| view: context.getCurrentTexture().createView(), |
| storeOp: 'store', |
| |
| loadOp: 'clear', |
| }] |
| }); |
| renderPass.setPipeline(pipeline); |
| |
| renderPass.setVertexBuffer(0, vertexBuffer); |
| |
| renderPass.setBindGroup( 0, bindGroup ); |
| renderPass.draw(3); |
| renderPass.end(); |
| const commandBuffer = commandEncoder.finish(); |
| device.queue.submit([commandBuffer]); |
| </script> |
| </body> |
| |
| </html> |
| |
| const vertex = ` |
| // uniform关键字辅助var声明一个4x4矩阵变量 |
| //@group(0)的参数0对应webgpu代码.getBindGroupLayout(0)参数0 |
| //@binding(1)的参数对应webgpu代码.binding的值,保持一致,比如都是1 |
| @group(0) @binding(0) var<uniform> S:mat4x4<f32>; |
| @group(0) @binding(1) var<uniform> T:mat4x4<f32>; |
| @vertex |
| fn main(@location(0) pos: vec3<f32>) -> @builtin(position) vec4<f32> { |
| // 先缩放、后平移 |
| return T * S * vec4<f32>(pos,1.0);//缩放矩阵对顶点缩放变换 |
| } |
| ` |
| |
| |
| const fragment = ` |
| @fragment |
| fn main() -> @location(0) vec4<f32> { |
| return vec4<f32>(1.0, 0.0, 0.0, 1.0); |
| } |
| ` |
| |
| export { vertex, fragment } |
| |
参考
- threejs中文档,郭老师博客
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】凌霞软件回馈社区,博客园 & 1Panel & Halo 联合会员上线
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】博客园社区专享云产品让利特惠,阿里云新客6.5折上折
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 微软正式发布.NET 10 Preview 1:开启下一代开发框架新篇章
· 没有源码,如何修改代码逻辑?
· PowerShell开发游戏 · 打蜜蜂
· 在鹅厂做java开发是什么体验
· WPF到Web的无缝过渡:英雄联盟客户端的OpenSilver迁移实战