icy3dw/src/client/object/world/ClientWorldLoader.ts

48 lines
1.3 KiB
TypeScript

import { ImageLoader } from 'three';
import { to1D } from '../../../common/convert';
import { WorldLoader } from '../../../common/world/WorldLoader';
const loader = new ImageLoader();
const worldPath = '/assets/terrain/region/';
export class ClientWorldLoader implements WorldLoader {
async loadHeightMap(
chunkX: number,
chunkY: number,
scale: number,
): Promise<number[]> {
return new Promise((resolve, reject) => {
loader.load(
`${worldPath}/height-${chunkX}-${chunkY}.png`,
(data) => resolve(ClientWorldLoader.heightFromImage(data, scale)),
undefined,
(err) => {
reject(err);
},
);
});
}
public static heightFromImage(
image: HTMLImageElement,
scale: number,
): number[] {
const array = new Array(image.width * image.height);
const ctx = document.createElement('canvas').getContext('2d');
ctx.canvas.width = image.width;
ctx.canvas.height = image.height;
ctx.drawImage(image, 0, 0, image.width, image.height);
// pixel data
const data = ctx.getImageData(0, 0, image.width, image.height);
for (let x = 0; x < image.width; x++) {
for (let y = 0; y < image.height; y++) {
const index = to1D(x, y, image.width);
array[index] = (data.data[index * 4] * scale) / 255;
}
}
return array;
}
}