import { assert } from "https://deno.land/std@0.221.0/assert/assert.ts"; import { v2 } from "../../common/utils.ts"; import { Vec2 } from "../../common/utils.ts"; import { CompDisplay } from "../components/display.ts"; import { query_in_rect } from "../components/world.ts"; import { CompPos } from "../components/world.ts"; import { CompId, Query } from "../engine.ts"; import { Engine } from "../engine.ts"; import { CompPlayer } from "./player.ts"; export class CompEnemy { target; life; constructor() { this.target = null as number | null; this.life = 10; } find_target_from(engine: Engine, pos: Vec2, range: number) { const radius = v2(range, range); const found = engine.one(Query.with(CompPlayer).with(CompId).and(query_in_rect(pos.sub(radius), pos.add(radius)))); if (found === null) { this.target = null; return; } const [_, id, __] = found; this.target = id.id; } get_target_pos(engine: Engine) { if (this.target === null) return null; const result = engine.one(Query.with(CompId).filter(([c]) => c.id === this.target).with(CompPos)); if (result === null) { this.target = null; return null; } const [_, pos] = result; return pos.pos; } } export function sys_spawn_enemy(pos: Vec2) { return (engine: Engine) => { return engine.spawn((entity) => entity.insert( new CompEnemy(), new CompPos(entity, pos), new CompDisplay("èé"), ) ); }; } export function sys_update_enemy() { const trigger_range = 5; const forget_range = 10; return (engine: Engine) => { for (const [enemy, enemy_pos] of engine.all(Query.with(CompEnemy).with(CompPos))) { if (enemy.target === null) enemy.find_target_from(engine, enemy_pos.pos, trigger_range); const pos = enemy.get_target_pos(engine); if (pos === null) continue; const direction = pos.sub(enemy_pos.pos); if (direction.len() <= forget_range) { const displacement = direction.normalize(); const moved = enemy_pos.move_collide(engine, displacement); if (!moved) { enemy_pos.move_collide(engine, v2(displacement.x(), 0)); enemy_pos.move_collide(engine, v2(0, displacement.y())); } } else enemy.target = null; } }; } export function enemy_plugin(engine: Engine) { engine.global_system_loop(sys_update_enemy(), 500); }