/// import { aabb_overlap } from "./helper.ts"; import { WSLoader } from "./loader.ts"; import { AABB, get_graphics_part, get_prefab, get_respackentry, get_spatialindex, GraphicsPart, Prefab, Resource, SpatialIndex } from "./resources.ts"; const canvas = document.createElement("canvas") canvas.style.position = "absolute" canvas.style.top = "0px" canvas.style.left = "0px" canvas.style.width = "100vw" canvas.style.height = "100vh" document.body.append(canvas) const ctx = canvas.getContext("2d")! let thing: Thing | undefined; const loader = new WSLoader() function draw() { ctx.fillStyle = "black" ctx.fillRect(0, 0, canvas.width, canvas.height) ctx.fillStyle = "white" ctx.font = "64px sans-serif" ctx.fillText(`${loader.num_loading}`, 20, 80) thing?.root.draw() requestAnimationFrame(draw) } function resize() { canvas.width = globalThis.innerWidth canvas.height = globalThis.innerHeight } globalThis.addEventListener("resize", () => resize()) resize() draw() async function init() { await loader.wait_ready() const entry_res = await loader.get_entry() const entry = await get_respackentry(loader, entry_res) const root = await get_spatialindex(loader, entry.c_spatial_index!) thing = new Thing(root) loader_loop() } async function loader_loop() { while (1) { await thing!.update() await new Promise(r => setTimeout(r, 100)) } } init() class Thing { view: AABB root: SNode constructor(root: SpatialIndex) { this.view = { min: { x: 0, y: 0, z: 0 }, max: { x: 1, y: 1, z: 1 } } this.root = new SNode(root) } async update() { await this.root.load(this.view) } } let num_loaded = 0 class SNode { children?: SNode[] prefab?: Prefab graphics?: GraphicsPart aabb?: AABB constructor(public data: SpatialIndex) { } async load_graphics() { if (this.data.prefab && !this.prefab) this.prefab = await get_prefab(loader, this.data.prefab) if (this.prefab?.graphics[0] && !this.graphics) this.graphics = await get_graphics_part(loader, this.prefab.graphics[0][1]) } async load(view: AABB) { if (!this.aabb || aabb_overlap(this.aabb, view)) { if (this.children) { await Promise.all(this.children.map(c => c.load(view))) } else if (this.data.child.length) { if (num_loaded > 300) return num_loaded += 1 this.children = await Promise.all(this.data.child.map(async c => { const n = new SNode(await get_spatialindex(loader, c[1])) n.aabb = c[0] await n.load_graphics() return n })) } } else { if (this.children) { num_loaded -= 1 this.children = undefined } } } draw() { if (this.children) return this.children.forEach(c => c.draw()) if (!this.graphics) return ctx.fillStyle = "red" ctx.save() ctx.scale(100000, 100000) ctx.translate(-0.155, -0.63) ctx.translate(this.prefab!.transform![10], this.prefab!.transform![11]) for (const c of this.graphics.read()) { if (c.point) ctx.fillRect(c.point.z, c.point.y, 0.00001, 0.00001) } ctx.restore() } }