Recently, I am trying to learn to write some 3D games and share the results.
Strictly said is not a complete game, interested friends can watch.
- Preview the address: https://luosijie.github.io/ga…
- Git repository: https://github.com/luosijie/g…
- Language: the TypeScript
- Framework: Babylon,
To prepare
The only material used here: the little plane is simply designed in Blender
Blender is a free and open source modeling software for those interested in it. A tutorial for getting started is recommended on website B
Here are some of my steps
- Using simple geometric elements to build a model of the plane
- Make 2 small animations: propeller rotating and fuselage shaking
- Export the.glb format model
The code to import the model into Babylon is as follows
The main two parameters are meshes and animationGroups
{
animationGroups: (2) [AnimationGroup, AnimationGroup]
geometries: (9) [Geometry, Geometry, Geometry, Geometry, Geometry]
lights: []
meshes: (10) [Mesh, Mesh, Mesh, Mesh, Mesh, Mesh, Mesh, Mesh, Mesh, Mesh]
particleSystems: []
skeletons: []
transformNodes: (5) [TransformNode, TransformNode, TransformNode]
__proto__: Object
code
This project mainly realizes the following several links
- Basic scene construction
- The plane follows the mouse
- The formation and motion of particles
- A collision between a plane and a particle
Loading of aircraft models
Private async loadPlane(): Promise < any > {/ / create a transparent element package model const container. = MeshBuilder CreateBox (' plane - container, {width: 1, the depth: 2, height:1 }, this.scene) container.isVisible = false; / / adjust to the location and model superposition container bakeTransformIntoVertices (Matrix. Translation (0, 1.2, Y = -Math.pi / 2 container.position.x = 0.6 // LoadAirplane Model const GLB = await SceneLoader.ImportMeshAsync(null, './public/', 'plane.glb', this.scene) const root = glb.meshes[0] console.log('glb', Root.parent = container return {mesh: container, fly: () => { glb.animationGroups[0].play(true) glb.animationGroups[1].play(true) }, stop: () => { glb.animationGroups[0].stop(), glb.animationGroups[1].stop() } } }
Motion following of the aircraft model
- Obtain mouse coordinates and aircraft coordinates while the mouse is moving
- Aircraft coordinates require the conversion of 3D coordinates to screen coordinates
- Move the plane coordinates to the mouse coordinates
. / / get the mouse coordinates to store this. Scene. OnPointerObservable. Add (info = > {const {event} = info / / store the mouse coordinates data if (event. Type = = = 'pointermove') { this.pointerPos = { x: event.x, y: event.y } } }) ... Private updatePlane(); private updatePlane(); Void {// Set the smoothing coefficient - keep trying to get the value const smoothing = 2000 // Get the plane screen coordinate const originPos = This.WorldToScreen (this.Plane. Mesh. Position) if (this.Pointerpos.x && this.Pointerpos.y) {const deltaX = (this.pointerPos.x - originPos.x) / smoothing const deltaY = (this.pointerPos.y - originPos.y) / smoothing // Plane moving in the direction of the mouse. This plane. The mesh. The position. X + = deltaX enclosing parts relate. Mesh. The position. - y = deltaY}}
Generate particles
/** * Particles are created for particles at every interval */ private InitParticles (): Void {// Particles = 90 const LIMIT = 90 this.particles = [] setInterval(() => {if (this.particles || this.state ! == State. Game) return const Particle = this.createParticle() // Set Particle = 20 + Math.random() * 20 Particle.position.y = -10 + Math. Random () * 20 Particle.position.z = 0 // Particles are inserted into particles: This. Particles. Push (Particle)}, 300)}
Update particle motion and detect if it has collided with an aircraft
/** Particles(); /** Particles(); Void {// const SPEED = 0.15 this.particles. Foreach ((e, index) => {// After the particles have almost left the screen, X = 20 + Math.random() * 20} e.Correction. X -= SPEED // Detect whether a particle has collide with a plane const collided = e.intersectsMesh(this.plane.mesh) if (collided) { this.particles.splice(index, 1) e.dispose() if (e.name === 'sphere') { this.score++ this.updateScore() console.log('collided') } } }) }
other
This is the main process of the project and some others, such as:
- Scene construction
- Camera processing
- Lighting treatment
- Game state handling
Check out the full code on GitHub
Thank you for reading
If you like, thumb up Star support