mirror of
https://github.com/visgl/luma.gl.git
synced 2025-12-08 17:36:19 +00:00
181 lines
4.0 KiB
Plaintext
181 lines
4.0 KiB
Plaintext
import {DeviceTabs} from '@site/src/react-luma';
|
|
import {HelloTriangleExample} from '@site';
|
|
|
|
# Hello Triangle
|
|
|
|
This tutorial will demonstrate how to draw a triangle using luma.gl's high-level APIs.
|
|
|
|
<DeviceTabs />
|
|
<HelloTriangleExample />
|
|
|
|
It is assumed you've set up your development environment as described in
|
|
[Getting Started](/docs/getting-started). Your `index.js` file should look like the following:
|
|
|
|
```typescript
|
|
import {AnimationLoop} from '@luma.gl/engine';
|
|
import {clear} from '@luma.gl/webgl';
|
|
|
|
class AppAnimationLoop extends AnimationLoop ({
|
|
override onInitialize({device}) {
|
|
// Setup logic goes here
|
|
},
|
|
|
|
override onRender({device}) {
|
|
// Drawing logic goes here
|
|
clear(device, {color: [0, 0, 0, 1]});
|
|
}
|
|
});
|
|
|
|
const loop = new AppAnimationLoop();
|
|
loop.start();
|
|
```
|
|
|
|
First, we'll need to update our imports with the classes we'll be using, `Buffer` and `Model`:
|
|
|
|
```typescript
|
|
import {AnimationLoop, Model} from '@luma.gl/engine';
|
|
import {clear} from '@luma.gl/webgl';
|
|
```
|
|
|
|
Now let's create some buffers in the `onInitialize` method to hold our attribute data:
|
|
|
|
```typescript
|
|
override onInitialize({device}) {
|
|
// Setup logic goes here
|
|
const positionBuffer = device.createBuffer(new Float32Array([
|
|
-0.5, -0.5,
|
|
0.5, -0.5,
|
|
0.0, 0.5
|
|
]));
|
|
|
|
const colorBuffer = device.createBuffer(new Float32Array([
|
|
1.0, 0.0, 0.0,
|
|
0.0, 1.0, 0.0,
|
|
0.0, 0.0, 1.0
|
|
]));
|
|
}
|
|
```
|
|
|
|
Next let's add the vertex and fragment shader code we'll be using to draw:
|
|
|
|
```typescript
|
|
override onInitialize({device}) {
|
|
// Setup logic goes here
|
|
|
|
// Buffers...
|
|
|
|
const vs = `
|
|
attribute vec2 position;
|
|
attribute vec3 color;
|
|
|
|
varying vec3 vColor;
|
|
|
|
void main() {
|
|
vColor = color;
|
|
gl_Position = vec4(position, 0.0, 1.0);
|
|
}
|
|
`;
|
|
|
|
const fs = `
|
|
varying vec3 vColor;
|
|
|
|
void main() {
|
|
gl_FragColor = vec4(vColor, 1.0);
|
|
}
|
|
`;
|
|
|
|
}
|
|
```
|
|
|
|
As a final step in our initialization, we'll create a `Model` in `onInitialize`:
|
|
|
|
```typescript
|
|
override onInitialize({device}) {
|
|
// Setup logic goes here
|
|
|
|
// Buffers...
|
|
|
|
// Shaders...
|
|
|
|
this.model = new Model(device, {
|
|
vs,
|
|
fs,
|
|
attributes: {
|
|
position: positionBuffer,
|
|
color: colorBuffer
|
|
},
|
|
vertexCount: 3
|
|
});
|
|
|
|
return {model};
|
|
}
|
|
```
|
|
|
|
A `Model` can be thought of as gathering all the WebGL pieces necessary for a single draw call: programs, attributes, uniforms. Also note that we return the `Model` instance we created. This will make it available to the `onRender` method.
|
|
|
|
Our `onRender` method is comparitavely much simpler:
|
|
|
|
```typescript
|
|
override onRender({device}) {
|
|
clear(device, {color: [0, 0, 0, 1]});
|
|
this.model.draw();
|
|
}
|
|
```
|
|
|
|
This clears the canvas and draws the `Model`. If all went well, you should see a tri-color triangle on a black background.
|
|
|
|
The entire application should look like the following:
|
|
|
|
```typescript
|
|
import {AnimationLoop, Model} from '@luma.gl/engine';
|
|
import {clear} from '@luma.gl/webgl';
|
|
|
|
class AppAnimationLoop extends AnimationLoop {
|
|
override onInitialize({device}) {
|
|
const positionBuffer = device.createBuffer(new Float32Array([-0.5, -0.5, 0.5, -0.5, 0.0, 0.5]));
|
|
|
|
const colorBuffer = device.createBuffer(new Float32Array([1.0, 0.0, 0.0, 0.0, 1.0, 0.0, 0.0, 0.0, 1.0]));
|
|
|
|
const vs = `
|
|
attribute vec2 position;
|
|
attribute vec3 color;
|
|
|
|
varying vec3 vColor;
|
|
|
|
void main() {
|
|
vColor = color;
|
|
gl_Position = vec4(position, 0.0, 1.0);
|
|
}
|
|
`;
|
|
|
|
const fs = `
|
|
varying vec3 vColor;
|
|
|
|
void main() {
|
|
gl_FragColor = vec4(vColor, 1.0);
|
|
}
|
|
`;
|
|
|
|
const model = new Model(device, {
|
|
vs,
|
|
fs,
|
|
attributes: {
|
|
position: positionBuffer,
|
|
color: colorBuffer
|
|
},
|
|
vertexCount: 3
|
|
});
|
|
|
|
return {model};
|
|
},
|
|
|
|
override onRender({device, model}) {
|
|
clear(device, {color: [0, 0, 0, 1]});
|
|
model.draw();
|
|
}
|
|
};
|
|
|
|
const loop = new AppAnimationLoop();
|
|
loop.start();
|
|
```
|