Skip to content

Commit

Permalink
Implement rocket and level module
Browse files Browse the repository at this point in the history
  • Loading branch information
phisn committed Sep 21, 2024
1 parent 926d41f commit a882bb3
Show file tree
Hide file tree
Showing 5 changed files with 149 additions and 16 deletions.
4 changes: 0 additions & 4 deletions packages/game/src/model/point.ts

This file was deleted.

1 change: 1 addition & 0 deletions packages/game/src/model/store.ts
Original file line number Diff line number Diff line change
Expand Up @@ -49,4 +49,5 @@ export interface GameEvents {
}): void

captureChanged(props: { rocket: RocketEntity; level: LevelEntity; started: boolean }): void
captured(props: { rocket: RocketEntity; level: LevelEntity }): void
}
Original file line number Diff line number Diff line change
@@ -1,12 +1,29 @@
import cos from "@stdlib/math/base/special/cos"
import sin from "@stdlib/math/base/special/sin"

export interface Point {
x: number
y: number
}

export interface Rect {
left: number
top: number
right: number
bottom: number
}

export interface Size {
width: number
height: number
}

export const changeAnchor = (
position: { x: number; y: number },
position: Point,
rotation: number,
size: { width: number; height: number },
sourceAnchor: { x: number; y: number },
targetAnchor: { x: number; y: number },
size: Size,
sourceAnchor: Point,
targetAnchor: Point,
) => ({
x:
position.x +
Expand Down
131 changes: 125 additions & 6 deletions packages/game/src/modules/module-level.ts
Original file line number Diff line number Diff line change
@@ -1,10 +1,17 @@
import { LevelConfig } from "../../proto/world"
import { EntityWith } from "../framework/entity"
import { GameInput } from "../game"
import { GameComponents, GameStore } from "../model/store"
import { Point, Rect, Size, changeAnchor } from "../model/utils"
import { RocketEntity, rocketComponents } from "./module-rocket"

export interface LevelComponent {
config: LevelConfig

capturing: boolean
completed: boolean

cameraRect: Rect
}

export const levelComponents = ["level", "body"] satisfies (keyof GameComponents)[]
Expand All @@ -28,22 +35,61 @@ export class ModuleLevel {
})
}

onReset() {}
onReset() {
this.progress = undefined
this.progressLevel = undefined

for (const level of this.store.entities.multipleCopy(...levelComponents)) {
this.store.entities.remove(level)
}

const config = this.store.resources.get("config")

let nearestLevel: LevelEntity | undefined
let nearestDistance = Infinity

for (const levelConfig of config.levels) {
const level = this.constructLevel(levelConfig)

const distance = Math.sqrt(
(levelConfig.positionX - config.rocket.positionX) ** 2 +
(levelConfig.positionY - config.rocket.positionY) ** 2,
)

if (distance < nearestDistance) {
nearestDistance = distance
nearestLevel = level
}
}

if (nearestLevel === undefined) {
throw new Error("No levels")
}

const level = nearestLevel.get("level")
level.completed = true
}

onUpdate(_input: GameInput) {
if (this.progress && this.progressLevel) {
this.progress -= 1

if (this.progress <= 0) {
const world = this.store.resources.get("world")

const body = this.progressLevel.get("body")
const level = this.progressLevel.get("level")
const captured = this.progressLevel
this.progressLevel = undefined

const world = this.store.resources.get("world")
const body = captured.get("body")
world.removeRigidBody(body)

const level = captured.get("level")
level.completed = true
this.progressLevel = undefined
level.capturing = false

this.store.events.invoke.captured?.({
rocket: this.store.entities.single(...rocketComponents)(),
level: captured,
})
}
}
}
Expand All @@ -52,9 +98,13 @@ export class ModuleLevel {
if (started) {
this.progress = TICKS_TO_CAPTURE
this.progressLevel = level

level.get("level").capturing = true
} else {
this.progress = undefined
this.progressLevel = undefined

level.get("level").capturing = false
}

this.store.events.invoke.captureChanged?.({
Expand All @@ -63,6 +113,75 @@ export class ModuleLevel {
started,
})
}

private constructLevel(levelConfig: LevelConfig) {
const rapier = this.store.resources.get("rapier")
const world = this.store.resources.get("world")

const body = world.createRigidBody(new rapier.RigidBodyDesc(rapier.RigidBodyType.Fixed))

const captureBox = calculateCaptureBox(
{ x: levelConfig.positionX, y: levelConfig.positionY },
levelConfig.rotation,
levelConfig.captureAreaLeft,
levelConfig.captureAreaRight,
)

world.createCollider(
rapier.ColliderDesc.cuboid(captureBox.size.width, captureBox.size.height)
.setTranslation(captureBox.transformed.x, captureBox.transformed.y)
.setRotation(levelConfig.rotation)
.setSensor(true),
body,
)

const level = this.store.entities.create({
body,
level: {
config: levelConfig,

capturing: false,
completed: false,

cameraRect: {
left: levelConfig.cameraTopLeftX,
top: levelConfig.cameraTopLeftY,
right: levelConfig.cameraBottomRightX,
bottom: levelConfig.cameraBottomRightY,
},
},
})

return level
}
}

const TICKS_TO_CAPTURE = 60
const FLAG_CAPTURE_HEIGHT = 0.5

const LEVEL_SIZE: Size = {
width: 1.65,
height: 2.616,
}

function calculateCaptureBox(
position: Point,
rotation: number,
captureDistanceLeft: number,
captureDistanceRight: number,
) {
const transformed = changeAnchor(
{ x: position.x, y: position.y },
rotation,
LEVEL_SIZE,
{ x: 0.5, y: 1 },
{ x: 0.2, y: 0 },
)

const size = {
width: captureDistanceLeft + captureDistanceRight,
height: FLAG_CAPTURE_HEIGHT,
}

return { size, transformed }
}
4 changes: 2 additions & 2 deletions packages/game/src/modules/module-rocket.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import { EntityWith } from "../framework/entity"
import { GameInput } from "../game"
import { changeAnchor } from "../model/change-anchor"
import { GameComponents, GameStore } from "../model/store"
import { Size, changeAnchor } from "../model/utils"

export interface RocketComponent {
thrust: boolean
Expand Down Expand Up @@ -87,7 +87,7 @@ const ROCKET_COLLIDERS = [
[-0.9, -1.8, -0.894, -1.212, -0.24, -1.212],
]

export const ROCKET_SIZE = {
export const ROCKET_SIZE: Size = {
width: 1.8,
height: 3.6,
}

0 comments on commit a882bb3

Please sign in to comment.