Compare commits
3 commits
next
...
world-data
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
5e4bde18a7 | ||
|
|
4cf578b774 | ||
|
|
7a88b35ae2 |
6 changed files with 221 additions and 47 deletions
62
buildWorkers.mjs
Normal file
62
buildWorkers.mjs
Normal file
|
|
@ -0,0 +1,62 @@
|
|||
// main worker file intended for computing world geometry is built using prismarine-viewer/buildWorker.mjs
|
||||
import { build, context } from 'esbuild'
|
||||
import fs from 'fs'
|
||||
import { sharedPlugins } from './scripts/esbuildPlugins.mjs'
|
||||
|
||||
const watch = process.argv.includes('-w')
|
||||
|
||||
const result = await (watch ? context : build)({
|
||||
bundle: true,
|
||||
platform: 'browser',
|
||||
entryPoints: [/* 'prismarine-viewer/examples/webglRendererWorker.ts', */'src/worldSaveWorker.ts'],
|
||||
outdir: 'prismarine-viewer/public/',
|
||||
sourcemap: watch ? 'inline' : 'external',
|
||||
minify: !watch,
|
||||
treeShaking: true,
|
||||
logLevel: 'info',
|
||||
alias: {
|
||||
'three': './node_modules/three/src/Three.js',
|
||||
events: 'events', // make explicit
|
||||
buffer: 'buffer',
|
||||
'fs': 'browserfs/dist/shims/fs.js',
|
||||
http: 'http-browserify',
|
||||
perf_hooks: './src/perf_hooks_replacement.js',
|
||||
crypto: './src/crypto.js',
|
||||
stream: 'stream-browserify',
|
||||
net: 'net-browserify',
|
||||
assert: 'assert',
|
||||
dns: './src/dns.js'
|
||||
},
|
||||
inject: [
|
||||
'./src/shims.js'
|
||||
],
|
||||
plugins: [
|
||||
{
|
||||
name: 'writeOutput',
|
||||
setup (build) {
|
||||
build.onEnd(({ outputFiles }) => {
|
||||
for (const file of outputFiles) {
|
||||
for (const dir of ['prismarine-viewer/public', 'dist']) {
|
||||
const baseName = file.path.split('/').pop()
|
||||
fs.writeFileSync(`${dir}/${baseName}`, file.contents)
|
||||
}
|
||||
}
|
||||
})
|
||||
}
|
||||
},
|
||||
...sharedPlugins
|
||||
],
|
||||
loader: {
|
||||
'.vert': 'text',
|
||||
'.frag': 'text'
|
||||
},
|
||||
mainFields: [
|
||||
'browser', 'module', 'main'
|
||||
],
|
||||
keepNames: true,
|
||||
write: false,
|
||||
})
|
||||
|
||||
if (watch) {
|
||||
await result.watch()
|
||||
}
|
||||
|
|
@ -18,7 +18,7 @@ const watchExternal = [
|
|||
]
|
||||
|
||||
/** @type {import('esbuild').Plugin[]} */
|
||||
const plugins = [
|
||||
const sharedPlugins = [
|
||||
{
|
||||
name: 'strict-aliases',
|
||||
setup (build) {
|
||||
|
|
@ -65,6 +65,53 @@ const plugins = [
|
|||
})
|
||||
}
|
||||
},
|
||||
{
|
||||
name: 'fix-dynamic-require',
|
||||
setup (build) {
|
||||
build.onResolve({
|
||||
filter: /1\.14\/chunk/,
|
||||
}, async ({ resolveDir, path }) => {
|
||||
if (!resolveDir.includes('prismarine-provider-anvil')) return
|
||||
return {
|
||||
namespace: 'fix-dynamic-require',
|
||||
path,
|
||||
pluginData: {
|
||||
resolvedPath: `${join(resolveDir, path)}.js`,
|
||||
resolveDir
|
||||
},
|
||||
}
|
||||
})
|
||||
build.onLoad({
|
||||
filter: /.+/,
|
||||
namespace: 'fix-dynamic-require',
|
||||
}, async ({ pluginData: { resolvedPath, resolveDir } }) => {
|
||||
const resolvedFile = await fs.promises.readFile(resolvedPath, 'utf8')
|
||||
return {
|
||||
contents: resolvedFile.replace("require(`prismarine-chunk/src/pc/common/BitArray${noSpan ? 'NoSpan' : ''}`)", "noSpan ? require(`prismarine-chunk/src/pc/common/BitArray`) : require(`prismarine-chunk/src/pc/common/BitArrayNoSpan`)"),
|
||||
resolveDir,
|
||||
loader: 'js',
|
||||
}
|
||||
})
|
||||
}
|
||||
},
|
||||
polyfillNode({
|
||||
polyfills: {
|
||||
fs: false,
|
||||
dns: false,
|
||||
crypto: false,
|
||||
events: false,
|
||||
http: false,
|
||||
stream: false,
|
||||
buffer: false,
|
||||
perf_hooks: false,
|
||||
net: false,
|
||||
assert: false,
|
||||
},
|
||||
})
|
||||
]
|
||||
|
||||
/** @type {import('esbuild').Plugin[]} */
|
||||
const plugins = [
|
||||
{
|
||||
name: 'data-assets',
|
||||
setup (build) {
|
||||
|
|
@ -256,35 +303,6 @@ const plugins = [
|
|||
})
|
||||
}
|
||||
},
|
||||
{
|
||||
name: 'fix-dynamic-require',
|
||||
setup (build) {
|
||||
build.onResolve({
|
||||
filter: /1\.14\/chunk/,
|
||||
}, async ({ resolveDir, path }) => {
|
||||
if (!resolveDir.includes('prismarine-provider-anvil')) return
|
||||
return {
|
||||
namespace: 'fix-dynamic-require',
|
||||
path,
|
||||
pluginData: {
|
||||
resolvedPath: `${join(resolveDir, path)}.js`,
|
||||
resolveDir
|
||||
},
|
||||
}
|
||||
})
|
||||
build.onLoad({
|
||||
filter: /.+/,
|
||||
namespace: 'fix-dynamic-require',
|
||||
}, async ({ pluginData: { resolvedPath, resolveDir } }) => {
|
||||
const resolvedFile = await fs.promises.readFile(resolvedPath, 'utf8')
|
||||
return {
|
||||
contents: resolvedFile.replace("require(`prismarine-chunk/src/pc/common/BitArray${noSpan ? 'NoSpan' : ''}`)", "noSpan ? require(`prismarine-chunk/src/pc/common/BitArray`) : require(`prismarine-chunk/src/pc/common/BitArrayNoSpan`)"),
|
||||
resolveDir,
|
||||
loader: 'js',
|
||||
}
|
||||
})
|
||||
}
|
||||
},
|
||||
{
|
||||
name: 'react-displayname',
|
||||
setup (build) {
|
||||
|
|
@ -310,20 +328,7 @@ const plugins = [
|
|||
})
|
||||
}
|
||||
},
|
||||
polyfillNode({
|
||||
polyfills: {
|
||||
fs: false,
|
||||
dns: false,
|
||||
crypto: false,
|
||||
events: false,
|
||||
http: false,
|
||||
stream: false,
|
||||
buffer: false,
|
||||
perf_hooks: false,
|
||||
net: false,
|
||||
assert: false,
|
||||
},
|
||||
})
|
||||
...sharedPlugins
|
||||
]
|
||||
|
||||
export { plugins, connectedClients as clients }
|
||||
export { plugins, connectedClients as clients, sharedPlugins }
|
||||
|
|
|
|||
|
|
@ -9,5 +9,38 @@ export default () => {
|
|||
chatInputValueGlobal.value = '/warp '
|
||||
showModal({ reactType: 'chat' })
|
||||
})
|
||||
})
|
||||
});
|
||||
|
||||
(localServer as any).loadChunksOptimized = (chunks) => {
|
||||
const workersNum = 5
|
||||
const workers = [] as Worker[]
|
||||
|
||||
for (let i = 0; i < workersNum; i++) {
|
||||
const worker = new Worker('./worldSaveWorker.js')
|
||||
workers.push(worker)
|
||||
}
|
||||
|
||||
console.time('chunks-main')
|
||||
for (const [i, worker] of workers.entries()) {
|
||||
worker.postMessage({
|
||||
type: 'readChunks',
|
||||
chunks: chunks.slice(i * chunks.length / workersNum, (i + 1) * chunks.length / workersNum),
|
||||
folder: localServer!.options.worldFolder + '/region'
|
||||
})
|
||||
}
|
||||
|
||||
let finishedWorkers = 0
|
||||
|
||||
for (const worker of workers) {
|
||||
// eslint-disable-next-line @typescript-eslint/no-loop-func
|
||||
worker.onmessage = (msg) => {
|
||||
if (msg.data.type === 'done') {
|
||||
finishedWorkers++
|
||||
if (finishedWorkers === workersNum) {
|
||||
console.timeEnd('chunks-main')
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -63,7 +63,6 @@ export default ({ indicators, effects }: {indicators: typeof defaultIndicatorsSt
|
|||
}, [effects])
|
||||
|
||||
useEffect(() => {
|
||||
// todo use more precise timer for each effect
|
||||
const interval = setInterval(() => {
|
||||
for (const [index, effect] of effectsRef.current.entries()) {
|
||||
if (effect.time === 0) {
|
||||
|
|
|
|||
3
src/workerWorkaround.ts
Normal file
3
src/workerWorkaround.ts
Normal file
|
|
@ -0,0 +1,3 @@
|
|||
global = globalThis
|
||||
globalThis.window = globalThis
|
||||
window.mcData = {}
|
||||
72
src/worldSaveWorker.ts
Normal file
72
src/worldSaveWorker.ts
Normal file
|
|
@ -0,0 +1,72 @@
|
|||
import './workerWorkaround'
|
||||
import fs from 'fs'
|
||||
import './fs2'
|
||||
import { Anvil } from 'prismarine-provider-anvil'
|
||||
import WorldLoader from 'prismarine-world'
|
||||
|
||||
import * as browserfs from 'browserfs'
|
||||
import { generateSpiralMatrix } from 'flying-squid/dist/utils'
|
||||
import '../dist/mc-data/1.14'
|
||||
import { oneOf } from '@zardoy/utils'
|
||||
|
||||
console.log('install')
|
||||
browserfs.install(window)
|
||||
window.fs = fs
|
||||
|
||||
onmessage = (msg) => {
|
||||
globalThis.readSkylight = false
|
||||
if (msg.data.type === 'readChunks') {
|
||||
browserfs.configure({
|
||||
fs: 'MountableFileSystem',
|
||||
options: {
|
||||
'/data': { fs: 'IndexedDB' },
|
||||
},
|
||||
}, async () => {
|
||||
const version = '1.14.4'
|
||||
const AnvilLoader = Anvil(version)
|
||||
const World = WorldLoader(version)
|
||||
// const folder = '/data/worlds/Greenfield v0.5.3-3/region'
|
||||
const { folder } = msg.data
|
||||
const world = new World(() => {
|
||||
throw new Error('Not implemented')
|
||||
}, new AnvilLoader(folder))
|
||||
// const chunks = generateSpiralMatrix(20)
|
||||
const { chunks } = msg.data
|
||||
// const spawn = {
|
||||
// x: 113,
|
||||
// y: 64,
|
||||
|
||||
// }
|
||||
console.log('starting...')
|
||||
console.time('columns')
|
||||
const loadedColumns = [] as any[]
|
||||
const columnToTransfarable = (chunk) => {
|
||||
return {
|
||||
biomes: chunk.biomes,
|
||||
// blockEntities: chunk.blockEntities,
|
||||
// sectionMask: chunk.sectionMask,
|
||||
sections: chunk.sections,
|
||||
// skyLightMask: chunk.skyLightMask,
|
||||
// blockLightMask: chunk.blockLightMask,
|
||||
// skyLightSections: chunk.skyLightSections,
|
||||
// blockLightSections: chunk.blockLightSections
|
||||
}
|
||||
}
|
||||
|
||||
for (const chunk of chunks) {
|
||||
const column = await world.getColumn(chunk[0], chunk[1])
|
||||
if (!column) throw new Error(`Column ${chunk[0]} ${chunk[1]} not found`)
|
||||
postMessage({
|
||||
column: columnToTransfarable(column)
|
||||
})
|
||||
}
|
||||
postMessage({
|
||||
type: 'done',
|
||||
})
|
||||
|
||||
console.timeEnd('columns')
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
// window.fs = fs
|
||||
Loading…
Add table
Add a link
Reference in a new issue