minerender 2.1.0-alpha.114 → 2.1.0-alpha.116
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/browser/index.d.mts +199 -13
- package/dist/browser/index.d.ts +199 -13
- package/dist/browser/index.js +939 -231
- package/dist/browser/index.js.map +1 -1
- package/dist/browser/index.mjs +885 -177
- package/dist/browser/index.mjs.map +1 -1
- package/dist/browser/section.worker.js +6 -3
- package/dist/browser/section.worker.js.map +1 -1
- package/dist/browser/section.worker.mjs +6 -3
- package/dist/browser/section.worker.mjs.map +1 -1
- package/dist/bundle.js +903 -139
- package/dist/bundle.js.map +1 -1
- package/dist/node/index.d.mts +199 -13
- package/dist/node/index.d.ts +199 -13
- package/dist/node/index.js +944 -231
- package/dist/node/index.js.map +1 -1
- package/dist/node/index.mjs +887 -177
- package/dist/node/index.mjs.map +1 -1
- package/package.json +1 -1
package/dist/bundle.js
CHANGED
|
@@ -4768,7 +4768,7 @@ var MineRender = (() => {
|
|
|
4768
4768
|
}
|
|
4769
4769
|
throw new Error(`THREE.TextureUtils: Unknown texture type ${type}.`);
|
|
4770
4770
|
}
|
|
4771
|
-
var REVISION, MOUSE, TOUCH, CullFaceNone, CullFaceBack, CullFaceFront, PCFShadowMap, PCFSoftShadowMap, VSMShadowMap, FrontSide, BackSide, DoubleSide, NoBlending, NormalBlending, AdditiveBlending, SubtractiveBlending, MultiplyBlending, CustomBlending, AddEquation, SubtractEquation, ReverseSubtractEquation, MinEquation, MaxEquation, ZeroFactor, OneFactor, SrcColorFactor, OneMinusSrcColorFactor, SrcAlphaFactor, OneMinusSrcAlphaFactor, DstAlphaFactor, OneMinusDstAlphaFactor, DstColorFactor, OneMinusDstColorFactor, SrcAlphaSaturateFactor, ConstantColorFactor, OneMinusConstantColorFactor, ConstantAlphaFactor, OneMinusConstantAlphaFactor, NeverDepth, AlwaysDepth, LessDepth, LessEqualDepth, EqualDepth, GreaterEqualDepth, GreaterDepth, NotEqualDepth, MultiplyOperation, MixOperation, AddOperation, NoToneMapping, LinearToneMapping, ReinhardToneMapping, CineonToneMapping, ACESFilmicToneMapping, CustomToneMapping, AgXToneMapping, NeutralToneMapping, UVMapping, CubeReflectionMapping, CubeRefractionMapping, EquirectangularReflectionMapping, EquirectangularRefractionMapping, CubeUVReflectionMapping, RepeatWrapping, ClampToEdgeWrapping, MirroredRepeatWrapping, NearestFilter, NearestMipmapNearestFilter, NearestMipmapLinearFilter, LinearFilter, LinearMipmapNearestFilter, LinearMipmapLinearFilter, UnsignedByteType, ByteType, ShortType, UnsignedShortType, IntType, UnsignedIntType, FloatType, HalfFloatType, UnsignedShort4444Type, UnsignedShort5551Type, UnsignedInt248Type, UnsignedInt5999Type, UnsignedInt101111Type, AlphaFormat, RGBFormat, RGBAFormat, DepthFormat, DepthStencilFormat, RedFormat, RedIntegerFormat, RGFormat, RGIntegerFormat, RGBAIntegerFormat, RGB_S3TC_DXT1_Format, RGBA_S3TC_DXT1_Format, RGBA_S3TC_DXT3_Format, RGBA_S3TC_DXT5_Format, RGB_PVRTC_4BPPV1_Format, RGB_PVRTC_2BPPV1_Format, RGBA_PVRTC_4BPPV1_Format, RGBA_PVRTC_2BPPV1_Format, RGB_ETC1_Format, RGB_ETC2_Format, RGBA_ETC2_EAC_Format, R11_EAC_Format, SIGNED_R11_EAC_Format, RG11_EAC_Format, SIGNED_RG11_EAC_Format, RGBA_ASTC_4x4_Format, RGBA_ASTC_5x4_Format, RGBA_ASTC_5x5_Format, RGBA_ASTC_6x5_Format, RGBA_ASTC_6x6_Format, RGBA_ASTC_8x5_Format, RGBA_ASTC_8x6_Format, RGBA_ASTC_8x8_Format, RGBA_ASTC_10x5_Format, RGBA_ASTC_10x6_Format, RGBA_ASTC_10x8_Format, RGBA_ASTC_10x10_Format, RGBA_ASTC_12x10_Format, RGBA_ASTC_12x12_Format, RGBA_BPTC_Format, RGB_BPTC_SIGNED_Format, RGB_BPTC_UNSIGNED_Format, RED_RGTC1_Format, SIGNED_RED_RGTC1_Format, RED_GREEN_RGTC2_Format, SIGNED_RED_GREEN_RGTC2_Format, InterpolateDiscrete, InterpolateLinear, InterpolateSmooth, InterpolateBezier, ZeroCurvatureEnding, ZeroSlopeEnding, WrapAroundEnding, TrianglesDrawMode, TriangleStripDrawMode, TriangleFanDrawMode, BasicDepthPacking, TangentSpaceNormalMap, ObjectSpaceNormalMap, NoColorSpace, SRGBColorSpace, LinearSRGBColorSpace, LinearTransfer, SRGBTransfer, KeepStencilOp, AlwaysStencilFunc, NeverCompare, LessCompare, EqualCompare, LessEqualCompare, GreaterCompare, NotEqualCompare, GreaterEqualCompare, AlwaysCompare, StaticDrawUsage, GLSL3, WebGLCoordinateSystem, WebGPUCoordinateSystem, _cache, _setConsoleFunction, ReversedDepthFuncs, EventDispatcher, _lut, _seed, DEG2RAD, RAD2DEG, MathUtils, _Vector2, Vector2, Quaternion, _Vector3, Vector3, _vector$c, _quaternion$5, _Matrix3, Matrix3, _m3, LINEAR_REC709_TO_XYZ, XYZ_TO_LINEAR_REC709, ColorManagement, _canvas, ImageUtils, _sourceId, TextureSource, _textureId, _tempVec3, Texture, _Vector4, Vector4, RenderTarget, WebGLRenderTarget, DataArrayTexture, Data3DTexture, _Matrix4, Matrix4, _v1$7, _m1$2, _zero, _one, _x, _y, _z, _matrix$2, _quaternion$4, Euler, Layers, _object3DId, _v1$6, _q1, _m1$1, _target, _position$4, _scale$3, _quaternion$3, _xAxis, _yAxis, _zAxis, _addedEvent, _removedEvent, _childaddedEvent, _childremovedEvent, Object3D, Group, _moveEvent, WebXRController, _colorKeywords, _hslA, _hslB, Color, _color, Scene, _v0$2, _v1$5, _v2$4, _v3$2, _vab, _vac, _vbc, _vap, _vbp, _vcp, _v40, _v41, _v42, Triangle, Box3, _points, _vector$b, _box$4, _v0$1, _v1$4, _v2$3, _f0, _f1, _f2, _center, _extents, _triangleNormal, _testAxis, _vector$a, _vector2$1, _id$2, BufferAttribute, Uint16BufferAttribute, Uint32BufferAttribute, Float32BufferAttribute, _box$3, _v1$3, _v2$2, Sphere, _id$1, _m1, _obj, _offset, _box$2, _boxMorphTargets, _vector$9, BufferGeometry, InterleavedBuffer, _vector$8, InterleavedBufferAttribute, _vector1, _vector2, _normalMatrix, Plane, _materialId, Material, _vector$7, _segCenter, _segDir, _diff, Ray, MeshBasicMaterial, _inverseMatrix$3, _ray$3, _sphere$6, _sphereHitAt, _vA, _vB, _vC, _tempA, _morphA, _intersectionPoint, _intersectionPointWorld, Mesh, DataTexture, InstancedBufferAttribute, _instanceLocalMatrix, _instanceWorldMatrix, _instanceIntersects, _box3, _identity, _mesh$1, _sphere$4, InstancedMesh, _sphere$3, _defaultSpriteCenter, _vector$6, Frustum, LineBasicMaterial, _vStart, _vEnd, _inverseMatrix$1, _ray$1, _sphere$1, _intersectPointOnRay, _intersectPointOnSegment, Line, _start, _end, LineSegments, CompressedTexture, CubeTexture, CanvasTexture, DepthTexture, CubeDepthTexture, ExternalTexture, BoxGeometry, _v0, _v1$1, _normal, _triangle, EdgesGeometry, PlaneGeometry, UniformsUtils, default_vertex, default_fragment, ShaderMaterial, RawShaderMaterial, MeshStandardMaterial, MeshDepthMaterial, MeshDistanceMaterial, Interpolant, CubicInterpolant, LinearInterpolant, DiscreteInterpolant, BezierInterpolant, KeyframeTrack, BooleanKeyframeTrack, ColorKeyframeTrack, NumberKeyframeTrack, QuaternionLinearInterpolant, QuaternionKeyframeTrack, StringKeyframeTrack, VectorKeyframeTrack, LoadingManager, DefaultLoadingManager, Loader, _position$2, _quaternion$2, _scale$2, Camera, _v3$1, _minTarget, _maxTarget, PerspectiveCamera, OrthographicCamera, fov, aspect, CubeCamera, ArrayCamera, _RESERVED_CHARS_RE, _reservedRe, _wordChar, _wordCharOrDot, _directoryRe, _nodeRe, _objectRe, _propertyRe, _trackRe, _supportedObjectNames, Composite, PropertyBinding, _controlInterpolantsResultBuffer, Uniform, _matrix, Raycaster, Spherical, _Matrix2, Matrix2, _vector$4, Box2, GridHelper, AxesHelper;
|
|
4771
|
+
var REVISION, MOUSE, TOUCH, CullFaceNone, CullFaceBack, CullFaceFront, PCFShadowMap, PCFSoftShadowMap, VSMShadowMap, FrontSide, BackSide, DoubleSide, NoBlending, NormalBlending, AdditiveBlending, SubtractiveBlending, MultiplyBlending, CustomBlending, AddEquation, SubtractEquation, ReverseSubtractEquation, MinEquation, MaxEquation, ZeroFactor, OneFactor, SrcColorFactor, OneMinusSrcColorFactor, SrcAlphaFactor, OneMinusSrcAlphaFactor, DstAlphaFactor, OneMinusDstAlphaFactor, DstColorFactor, OneMinusDstColorFactor, SrcAlphaSaturateFactor, ConstantColorFactor, OneMinusConstantColorFactor, ConstantAlphaFactor, OneMinusConstantAlphaFactor, NeverDepth, AlwaysDepth, LessDepth, LessEqualDepth, EqualDepth, GreaterEqualDepth, GreaterDepth, NotEqualDepth, MultiplyOperation, MixOperation, AddOperation, NoToneMapping, LinearToneMapping, ReinhardToneMapping, CineonToneMapping, ACESFilmicToneMapping, CustomToneMapping, AgXToneMapping, NeutralToneMapping, UVMapping, CubeReflectionMapping, CubeRefractionMapping, EquirectangularReflectionMapping, EquirectangularRefractionMapping, CubeUVReflectionMapping, RepeatWrapping, ClampToEdgeWrapping, MirroredRepeatWrapping, NearestFilter, NearestMipmapNearestFilter, NearestMipmapLinearFilter, LinearFilter, LinearMipmapNearestFilter, LinearMipmapLinearFilter, UnsignedByteType, ByteType, ShortType, UnsignedShortType, IntType, UnsignedIntType, FloatType, HalfFloatType, UnsignedShort4444Type, UnsignedShort5551Type, UnsignedInt248Type, UnsignedInt5999Type, UnsignedInt101111Type, AlphaFormat, RGBFormat, RGBAFormat, DepthFormat, DepthStencilFormat, RedFormat, RedIntegerFormat, RGFormat, RGIntegerFormat, RGBAIntegerFormat, RGB_S3TC_DXT1_Format, RGBA_S3TC_DXT1_Format, RGBA_S3TC_DXT3_Format, RGBA_S3TC_DXT5_Format, RGB_PVRTC_4BPPV1_Format, RGB_PVRTC_2BPPV1_Format, RGBA_PVRTC_4BPPV1_Format, RGBA_PVRTC_2BPPV1_Format, RGB_ETC1_Format, RGB_ETC2_Format, RGBA_ETC2_EAC_Format, R11_EAC_Format, SIGNED_R11_EAC_Format, RG11_EAC_Format, SIGNED_RG11_EAC_Format, RGBA_ASTC_4x4_Format, RGBA_ASTC_5x4_Format, RGBA_ASTC_5x5_Format, RGBA_ASTC_6x5_Format, RGBA_ASTC_6x6_Format, RGBA_ASTC_8x5_Format, RGBA_ASTC_8x6_Format, RGBA_ASTC_8x8_Format, RGBA_ASTC_10x5_Format, RGBA_ASTC_10x6_Format, RGBA_ASTC_10x8_Format, RGBA_ASTC_10x10_Format, RGBA_ASTC_12x10_Format, RGBA_ASTC_12x12_Format, RGBA_BPTC_Format, RGB_BPTC_SIGNED_Format, RGB_BPTC_UNSIGNED_Format, RED_RGTC1_Format, SIGNED_RED_RGTC1_Format, RED_GREEN_RGTC2_Format, SIGNED_RED_GREEN_RGTC2_Format, InterpolateDiscrete, InterpolateLinear, InterpolateSmooth, InterpolateBezier, ZeroCurvatureEnding, ZeroSlopeEnding, WrapAroundEnding, TrianglesDrawMode, TriangleStripDrawMode, TriangleFanDrawMode, BasicDepthPacking, TangentSpaceNormalMap, ObjectSpaceNormalMap, NoColorSpace, SRGBColorSpace, LinearSRGBColorSpace, LinearTransfer, SRGBTransfer, KeepStencilOp, AlwaysStencilFunc, NeverCompare, LessCompare, EqualCompare, LessEqualCompare, GreaterCompare, NotEqualCompare, GreaterEqualCompare, AlwaysCompare, StaticDrawUsage, GLSL3, WebGLCoordinateSystem, WebGPUCoordinateSystem, _cache, _setConsoleFunction, ReversedDepthFuncs, EventDispatcher, _lut, _seed, DEG2RAD, RAD2DEG, MathUtils, _Vector2, Vector2, Quaternion, _Vector3, Vector3, _vector$c, _quaternion$5, _Matrix3, Matrix3, _m3, LINEAR_REC709_TO_XYZ, XYZ_TO_LINEAR_REC709, ColorManagement, _canvas, ImageUtils, _sourceId, TextureSource, _textureId, _tempVec3, Texture, _Vector4, Vector4, RenderTarget, WebGLRenderTarget, DataArrayTexture, Data3DTexture, _Matrix4, Matrix4, _v1$7, _m1$2, _zero, _one, _x, _y, _z, _matrix$2, _quaternion$4, Euler, Layers, _object3DId, _v1$6, _q1, _m1$1, _target, _position$4, _scale$3, _quaternion$3, _xAxis, _yAxis, _zAxis, _addedEvent, _removedEvent, _childaddedEvent, _childremovedEvent, Object3D, Group, _moveEvent, WebXRController, _colorKeywords, _hslA, _hslB, Color, _color, Scene, _v0$2, _v1$5, _v2$4, _v3$2, _vab, _vac, _vbc, _vap, _vbp, _vcp, _v40, _v41, _v42, Triangle, Box3, _points, _vector$b, _box$4, _v0$1, _v1$4, _v2$3, _f0, _f1, _f2, _center, _extents, _triangleNormal, _testAxis, _vector$a, _vector2$1, _id$2, BufferAttribute, Uint16BufferAttribute, Uint32BufferAttribute, Float32BufferAttribute, _box$3, _v1$3, _v2$2, Sphere, _id$1, _m1, _obj, _offset, _box$2, _boxMorphTargets, _vector$9, BufferGeometry, InterleavedBuffer, _vector$8, InterleavedBufferAttribute, _vector1, _vector2, _normalMatrix, Plane, _materialId, Material, _vector$7, _segCenter, _segDir, _diff, Ray, MeshBasicMaterial, _inverseMatrix$3, _ray$3, _sphere$6, _sphereHitAt, _vA, _vB, _vC, _tempA, _morphA, _intersectionPoint, _intersectionPointWorld, Mesh, DataTexture, InstancedBufferAttribute, _instanceLocalMatrix, _instanceWorldMatrix, _instanceIntersects, _box3, _identity, _mesh$1, _sphere$4, InstancedMesh, _sphere$3, _defaultSpriteCenter, _vector$6, Frustum, LineBasicMaterial, _vStart, _vEnd, _inverseMatrix$1, _ray$1, _sphere$1, _intersectPointOnRay, _intersectPointOnSegment, Line, _start, _end, LineSegments, CompressedTexture, CubeTexture, CanvasTexture, DepthTexture, CubeDepthTexture, ExternalTexture, BoxGeometry, _v0, _v1$1, _normal, _triangle, EdgesGeometry, PlaneGeometry, UniformsUtils, default_vertex, default_fragment, ShaderMaterial, RawShaderMaterial, MeshStandardMaterial, MeshDepthMaterial, MeshDistanceMaterial, Interpolant, CubicInterpolant, LinearInterpolant, DiscreteInterpolant, BezierInterpolant, KeyframeTrack, BooleanKeyframeTrack, ColorKeyframeTrack, NumberKeyframeTrack, QuaternionLinearInterpolant, QuaternionKeyframeTrack, StringKeyframeTrack, VectorKeyframeTrack, LoadingManager, DefaultLoadingManager, Loader, _position$2, _quaternion$2, _scale$2, Camera, _v3$1, _minTarget, _maxTarget, PerspectiveCamera, OrthographicCamera, fov, aspect, CubeCamera, ArrayCamera, _RESERVED_CHARS_RE, _reservedRe, _wordChar, _wordCharOrDot, _directoryRe, _nodeRe, _objectRe, _propertyRe, _trackRe, _supportedObjectNames, Composite, PropertyBinding, _controlInterpolantsResultBuffer, Uniform, _matrix, Raycaster, Spherical, _Matrix2, Matrix2, _vector$4, Box2, GridHelper, AxesHelper, Controls;
|
|
4772
4772
|
var init_three_core = __esm({
|
|
4773
4773
|
"../../node_modules/three/build/three.core.js"() {
|
|
4774
4774
|
init_dirname();
|
|
@@ -20101,8 +20101,8 @@ var MineRender = (() => {
|
|
|
20101
20101
|
width *= view.width / fullWidth;
|
|
20102
20102
|
height *= view.height / fullHeight;
|
|
20103
20103
|
}
|
|
20104
|
-
const
|
|
20105
|
-
if (
|
|
20104
|
+
const skew2 = this.filmOffset;
|
|
20105
|
+
if (skew2 !== 0) left += near * skew2 / this.getFilmWidth();
|
|
20106
20106
|
this.projectionMatrix.makePerspective(left, left + width, top, top - height, near, this.far, this.coordinateSystem, this.reversedDepth);
|
|
20107
20107
|
this.projectionMatrixInverse.copy(this.projectionMatrix).invert();
|
|
20108
20108
|
}
|
|
@@ -21500,6 +21500,53 @@ var MineRender = (() => {
|
|
|
21500
21500
|
this.material.dispose();
|
|
21501
21501
|
}
|
|
21502
21502
|
};
|
|
21503
|
+
Controls = class extends EventDispatcher {
|
|
21504
|
+
/**
|
|
21505
|
+
* Constructs a new controls instance.
|
|
21506
|
+
*
|
|
21507
|
+
* @param {Object3D} object - The object that is managed by the controls.
|
|
21508
|
+
* @param {?HTMLElement} domElement - The HTML element used for event listeners.
|
|
21509
|
+
*/
|
|
21510
|
+
constructor(object4, domElement = null) {
|
|
21511
|
+
super();
|
|
21512
|
+
this.object = object4;
|
|
21513
|
+
this.domElement = domElement;
|
|
21514
|
+
this.enabled = true;
|
|
21515
|
+
this.state = -1;
|
|
21516
|
+
this.keys = {};
|
|
21517
|
+
this.mouseButtons = { LEFT: null, MIDDLE: null, RIGHT: null };
|
|
21518
|
+
this.touches = { ONE: null, TWO: null };
|
|
21519
|
+
}
|
|
21520
|
+
/**
|
|
21521
|
+
* Connects the controls to the DOM. This method has so called "side effects" since
|
|
21522
|
+
* it adds the module's event listeners to the DOM.
|
|
21523
|
+
*
|
|
21524
|
+
* @param {HTMLElement} element - The DOM element to connect to.
|
|
21525
|
+
*/
|
|
21526
|
+
connect(element) {
|
|
21527
|
+
if (this.domElement !== null) this.disconnect();
|
|
21528
|
+
this.domElement = element;
|
|
21529
|
+
}
|
|
21530
|
+
/**
|
|
21531
|
+
* Disconnects the controls from the DOM.
|
|
21532
|
+
*/
|
|
21533
|
+
disconnect() {
|
|
21534
|
+
}
|
|
21535
|
+
/**
|
|
21536
|
+
* Call this method if you no longer want use to the controls. It frees all internal
|
|
21537
|
+
* resources and removes all event listeners.
|
|
21538
|
+
*/
|
|
21539
|
+
dispose() {
|
|
21540
|
+
}
|
|
21541
|
+
/**
|
|
21542
|
+
* Controls should implement this method if they have to update their internal state
|
|
21543
|
+
* per simulation step.
|
|
21544
|
+
*
|
|
21545
|
+
* @param {number} [delta] - The time delta in seconds.
|
|
21546
|
+
*/
|
|
21547
|
+
update() {
|
|
21548
|
+
}
|
|
21549
|
+
};
|
|
21503
21550
|
if (typeof __THREE_DEVTOOLS__ !== "undefined") {
|
|
21504
21551
|
__THREE_DEVTOOLS__.dispatchEvent(new CustomEvent("register", { detail: {
|
|
21505
21552
|
revision: REVISION
|
|
@@ -41442,7 +41489,8 @@ void main() {
|
|
|
41442
41489
|
this.fontCache,
|
|
41443
41490
|
this.bannerPatternCache,
|
|
41444
41491
|
this.mineRenderDataCache,
|
|
41445
|
-
this.usernameUuidCache
|
|
41492
|
+
this.usernameUuidCache,
|
|
41493
|
+
this.biomeCache
|
|
41446
41494
|
];
|
|
41447
41495
|
}
|
|
41448
41496
|
/** Invalidates in-memory entries so later lookups reload them. Persisted entries are retained. */
|
|
@@ -41493,6 +41541,7 @@ void main() {
|
|
|
41493
41541
|
_Caching.bannerPatternCache = _Caching.createAssetCache();
|
|
41494
41542
|
_Caching.mineRenderDataCache = _Caching.createAssetCache();
|
|
41495
41543
|
_Caching.usernameUuidCache = Caches.builder().expireAfterWrite(Time.minutes(5)).expirationInterval(Time.seconds(30)).buildAsync();
|
|
41544
|
+
_Caching.biomeCache = _Caching.createAssetCache();
|
|
41496
41545
|
Caching = _Caching;
|
|
41497
41546
|
}
|
|
41498
41547
|
});
|
|
@@ -43258,7 +43307,7 @@ ${key}` : key, async () => {
|
|
|
43258
43307
|
case "blockStates":
|
|
43259
43308
|
return Object.values(value).every((property) => object(property) && "default" in property && Array.isArray(property.values));
|
|
43260
43309
|
case "blockTints":
|
|
43261
|
-
return ["constant", "grass", "stem", "redstone"].includes(value.source) && (value.source !== "constant" || Number.isInteger(value.color));
|
|
43310
|
+
return ["constant", "grass", "stem", "redstone"].includes(value.source) && (value.source !== "constant" || Number.isInteger(value.color)) && (value.biome === void 0 || ["grass", "foliage", "dry_foliage", "water"].includes(value.biome));
|
|
43262
43311
|
case "fluids":
|
|
43263
43312
|
return ["water", "lava"].includes(value.kind) && typeof value.renderModel === "boolean" && (value.levelProperty === void 0 || typeof value.levelProperty === "string");
|
|
43264
43313
|
case "dyes":
|
|
@@ -43414,15 +43463,19 @@ ${key}` : key, async () => {
|
|
|
43414
43463
|
Colormaps = class {
|
|
43415
43464
|
/** Samples the selected resource pack's grass colormap using Minecraft's climate coordinates. */
|
|
43416
43465
|
static async grassColor(origin, temperature = 0.5, downfall = 1) {
|
|
43417
|
-
|
|
43466
|
+
return this.getColor("grass", origin, temperature, downfall);
|
|
43467
|
+
}
|
|
43468
|
+
/** Samples a resource-pack colormap at the supplied climate coordinates. */
|
|
43469
|
+
static async getColor(kind, origin, temperature = 0.5, downfall = 1) {
|
|
43470
|
+
const key = AssetKey.parse("textures", `minecraft:colormap/${kind}`, origin);
|
|
43418
43471
|
const temp = Math.fround(temperature);
|
|
43419
43472
|
const rain = Math.fround(downfall) * temp;
|
|
43420
43473
|
const x4 = Math.floor((1 - temp) * 255), y5 = Math.floor((1 - rain) * 255);
|
|
43421
43474
|
return await Caching.blockTintCache.get(`${key.serialize()}|${x4},${y5}`, async () => {
|
|
43422
43475
|
const image = await ModelTextures.get(key);
|
|
43423
|
-
if (!image) throw new MineRenderError(`Missing
|
|
43476
|
+
if (!image) throw new MineRenderError(`Missing ${kind} colormap: ${key.toNamespacedString()}`);
|
|
43424
43477
|
if (image.width !== 256 || image.height !== 256) {
|
|
43425
|
-
throw new MineRenderError(
|
|
43478
|
+
throw new MineRenderError(`${kind} colormaps must be 256 \xD7 256 pixels`);
|
|
43426
43479
|
}
|
|
43427
43480
|
const [red, green, blue] = image.data.getImageData(x4, y5, 1, 1).data;
|
|
43428
43481
|
return red << 16 | green << 8 | blue;
|
|
@@ -57484,7 +57537,7 @@ ${key}` : key, async () => {
|
|
|
57484
57537
|
var base = 36;
|
|
57485
57538
|
var tMin = 1;
|
|
57486
57539
|
var tMax = 26;
|
|
57487
|
-
var
|
|
57540
|
+
var skew2 = 38;
|
|
57488
57541
|
var damp2 = 700;
|
|
57489
57542
|
var initialBias = 72;
|
|
57490
57543
|
var initialN = 128;
|
|
@@ -57573,7 +57626,7 @@ ${key}` : key, async () => {
|
|
|
57573
57626
|
) {
|
|
57574
57627
|
delta = floor(delta / baseMinusTMin);
|
|
57575
57628
|
}
|
|
57576
|
-
return floor(k4 + (baseMinusTMin + 1) * delta / (delta +
|
|
57629
|
+
return floor(k4 + (baseMinusTMin + 1) * delta / (delta + skew2));
|
|
57577
57630
|
};
|
|
57578
57631
|
var decode2 = function decode3(input) {
|
|
57579
57632
|
var output = [];
|
|
@@ -95332,6 +95385,7 @@ ${shader.fragmentShader}`.replace(
|
|
|
95332
95385
|
BannerPatterns: () => BannerPatterns,
|
|
95333
95386
|
BasicAssetKey: () => BasicAssetKey,
|
|
95334
95387
|
BatchedExecutor: () => BatchedExecutor,
|
|
95388
|
+
Biomes: () => Biomes,
|
|
95335
95389
|
BlockEntities: () => BlockEntities,
|
|
95336
95390
|
BlockObject: () => BlockObject,
|
|
95337
95391
|
BlockStateResolver: () => BlockStateResolver,
|
|
@@ -95365,6 +95419,7 @@ ${shader.fragmentShader}`.replace(
|
|
|
95365
95419
|
EntityObject: () => EntityObject,
|
|
95366
95420
|
Env: () => Env,
|
|
95367
95421
|
FluidModelObject: () => FluidModelObject,
|
|
95422
|
+
FlyControls: () => FlyControls,
|
|
95368
95423
|
Fonts: () => Fonts,
|
|
95369
95424
|
GUI_CONTAINER_LAYOUTS: () => GUI_CONTAINER_LAYOUTS,
|
|
95370
95425
|
Geometries: () => Geometries,
|
|
@@ -95467,6 +95522,7 @@ ${shader.fragmentShader}`.replace(
|
|
|
95467
95522
|
isDisposable: () => isDisposable,
|
|
95468
95523
|
isDoubleArray: () => isDoubleArray,
|
|
95469
95524
|
isEntityObject: () => isEntityObject,
|
|
95525
|
+
isFlyControls: () => isFlyControls,
|
|
95470
95526
|
isGuiObject: () => isGuiObject,
|
|
95471
95527
|
isInstanceManager: () => isInstanceManager,
|
|
95472
95528
|
isInstanceReference: () => isInstanceReference,
|
|
@@ -95792,6 +95848,122 @@ ${shader.fragmentShader}`.replace(
|
|
|
95792
95848
|
init_Assets();
|
|
95793
95849
|
init_BannerPatterns();
|
|
95794
95850
|
|
|
95851
|
+
// src/assets/Biomes.ts
|
|
95852
|
+
init_dirname();
|
|
95853
|
+
init_buffer2();
|
|
95854
|
+
init_process2();
|
|
95855
|
+
init_AssetKey();
|
|
95856
|
+
init_AssetLoader();
|
|
95857
|
+
init_AssetParsers();
|
|
95858
|
+
init_Caching();
|
|
95859
|
+
init_MineRenderError();
|
|
95860
|
+
init_Colormaps();
|
|
95861
|
+
|
|
95862
|
+
// src/assets/_biomes/SwampGrassColor.ts
|
|
95863
|
+
init_dirname();
|
|
95864
|
+
init_buffer2();
|
|
95865
|
+
init_process2();
|
|
95866
|
+
var permutation;
|
|
95867
|
+
var gradients = [[1, 1], [-1, 1], [1, -1], [-1, -1], [1, 0], [-1, 0], [1, 0], [-1, 0], [0, 1], [0, -1], [0, 1], [0, -1]];
|
|
95868
|
+
var skew = (Math.sqrt(3) - 1) / 2;
|
|
95869
|
+
var unskew = (3 - Math.sqrt(3)) / 6;
|
|
95870
|
+
function createPermutation() {
|
|
95871
|
+
const multiplier = 0x5deece66dn, mask = (1n << 48n) - 1n;
|
|
95872
|
+
let seed = 2345n ^ multiplier;
|
|
95873
|
+
const next = (bits2) => {
|
|
95874
|
+
seed = seed * multiplier + 11n & mask;
|
|
95875
|
+
return Number(seed >> BigInt(48 - bits2));
|
|
95876
|
+
};
|
|
95877
|
+
for (let i4 = 0; i4 < 3; i4++) {
|
|
95878
|
+
next(26);
|
|
95879
|
+
next(27);
|
|
95880
|
+
}
|
|
95881
|
+
const values = Uint8Array.from({ length: 256 }, (_4, i4) => i4);
|
|
95882
|
+
for (let i4 = 0; i4 < 256; i4++) {
|
|
95883
|
+
const bound = 256 - i4;
|
|
95884
|
+
let offset;
|
|
95885
|
+
if ((bound & bound - 1) === 0) offset = Math.floor(bound * next(31) / 2147483648);
|
|
95886
|
+
else {
|
|
95887
|
+
let bits2;
|
|
95888
|
+
do {
|
|
95889
|
+
bits2 = next(31);
|
|
95890
|
+
offset = bits2 % bound;
|
|
95891
|
+
} while (bits2 - offset + bound - 1 > 2147483647);
|
|
95892
|
+
}
|
|
95893
|
+
const other = i4 + offset;
|
|
95894
|
+
[values[i4], values[other]] = [values[other], values[i4]];
|
|
95895
|
+
}
|
|
95896
|
+
return values;
|
|
95897
|
+
}
|
|
95898
|
+
function swampGrassColor(x4, z4) {
|
|
95899
|
+
const p13 = permutation ?? (permutation = createPermutation());
|
|
95900
|
+
x4 *= 0.0225;
|
|
95901
|
+
z4 *= 0.0225;
|
|
95902
|
+
const s4 = (x4 + z4) * skew;
|
|
95903
|
+
const i4 = Math.floor(x4 + s4), j4 = Math.floor(z4 + s4);
|
|
95904
|
+
const t5 = (i4 + j4) * unskew;
|
|
95905
|
+
const dx = x4 - (i4 - t5), dz = z4 - (j4 - t5);
|
|
95906
|
+
const stepX = dx > dz ? 1 : 0, stepZ = 1 - stepX;
|
|
95907
|
+
const corner = (gx, gz, a4, b4) => {
|
|
95908
|
+
let falloff = 0.5 - a4 * a4 - b4 * b4;
|
|
95909
|
+
if (falloff < 0) return 0;
|
|
95910
|
+
const gradient = gradients[p13[gx + p13[gz & 255] & 255] % 12];
|
|
95911
|
+
falloff *= falloff;
|
|
95912
|
+
return falloff * falloff * (gradient[0] * a4 + gradient[1] * b4);
|
|
95913
|
+
};
|
|
95914
|
+
const noise = 70 * (corner(i4, j4, dx, dz) + corner(i4 + stepX, j4 + stepZ, dx - stepX + unskew, dz - stepZ + unskew) + corner(i4 + 1, j4 + 1, dx - 1 + 2 * unskew, dz - 1 + 2 * unskew));
|
|
95915
|
+
return noise < -0.1 ? 5011004 : 6975545;
|
|
95916
|
+
}
|
|
95917
|
+
|
|
95918
|
+
// src/assets/Biomes.ts
|
|
95919
|
+
var Biomes = class {
|
|
95920
|
+
/** Loads a biome registry entry, or returns `undefined` when no source provides it. */
|
|
95921
|
+
static async get(id, origin) {
|
|
95922
|
+
if (!/^(?:[a-z0-9_.-]+:)?[a-z0-9_./-]+$/.test(id)) throw new MineRenderError(`Invalid biome identifier: ${id}`);
|
|
95923
|
+
const [namespace, path] = id.includes(":") ? id.split(":") : ["minecraft", id];
|
|
95924
|
+
const key = new AssetKey(namespace, path, "worldgen", "biome", "data", ".json", origin?.root);
|
|
95925
|
+
return Caching.biomeCache.get(key.serialize(), async () => {
|
|
95926
|
+
const asset2 = await AssetLoader.get(key, "json" /* JSON */);
|
|
95927
|
+
if (asset2 === void 0) return void 0;
|
|
95928
|
+
if (!asset2 || typeof asset2 !== "object" || Array.isArray(asset2) || !asset2.effects || typeof asset2.effects !== "object" || Array.isArray(asset2.effects)) {
|
|
95929
|
+
throw new MineRenderError(`Invalid biome effects: ${id}`);
|
|
95930
|
+
}
|
|
95931
|
+
if (typeof asset2.temperature !== "number" || !Number.isFinite(asset2.temperature) || typeof asset2.downfall !== "number" || !Number.isFinite(asset2.downfall)) {
|
|
95932
|
+
throw new MineRenderError(`Invalid biome climate: ${id}`);
|
|
95933
|
+
}
|
|
95934
|
+
for (const kind of ["grass", "foliage", "dry_foliage", "water"]) {
|
|
95935
|
+
const color3 = asset2.effects[`${kind}_color`];
|
|
95936
|
+
if (color3 !== void 0) this.parseColor(color3, id, kind);
|
|
95937
|
+
}
|
|
95938
|
+
const modifier = asset2.effects.grass_color_modifier;
|
|
95939
|
+
if (modifier !== void 0 && modifier !== "none" && modifier !== "dark_forest" && modifier !== "swamp") {
|
|
95940
|
+
throw new MineRenderError(`Invalid biome grass color modifier: ${id}`);
|
|
95941
|
+
}
|
|
95942
|
+
return asset2;
|
|
95943
|
+
});
|
|
95944
|
+
}
|
|
95945
|
+
/** Returns packed sRGB, or `undefined` when the biome or requested water color is missing. */
|
|
95946
|
+
static async getColor(id, kind, origin, x4 = 0, z4 = 0) {
|
|
95947
|
+
const biome = await this.get(id, origin);
|
|
95948
|
+
if (!biome) return void 0;
|
|
95949
|
+
const rawColor = biome.effects[`${kind}_color`];
|
|
95950
|
+
let color3 = rawColor === void 0 ? void 0 : this.parseColor(rawColor, id, kind);
|
|
95951
|
+
if (kind === "water") return color3;
|
|
95952
|
+
const modifier = kind === "grass" ? biome.effects.grass_color_modifier : void 0;
|
|
95953
|
+
if (modifier === "swamp") return swampGrassColor(x4, z4);
|
|
95954
|
+
if (color3 === void 0) {
|
|
95955
|
+
const clamp2 = (value) => Math.max(0, Math.min(1, Math.fround(value)));
|
|
95956
|
+
color3 = await Colormaps.getColor(kind, origin, clamp2(biome.temperature), clamp2(biome.downfall));
|
|
95957
|
+
}
|
|
95958
|
+
return modifier === "dark_forest" ? (color3 & 16711422) + 2634762 >> 1 : color3;
|
|
95959
|
+
}
|
|
95960
|
+
static parseColor(value, id, kind) {
|
|
95961
|
+
if (typeof value === "string" && /^#[0-9a-fA-F]{6}$/.test(value)) return parseInt(value.slice(1), 16);
|
|
95962
|
+
if (typeof value === "number" && Number.isInteger(value) && value >= 0 && value <= 16777215) return value;
|
|
95963
|
+
throw new MineRenderError(`Invalid biome ${kind} color: ${id}`);
|
|
95964
|
+
}
|
|
95965
|
+
};
|
|
95966
|
+
|
|
95795
95967
|
// src/assets/BlockEntities.ts
|
|
95796
95968
|
init_dirname();
|
|
95797
95969
|
init_buffer2();
|
|
@@ -100396,8 +100568,20 @@ property list uchar int vertex_index
|
|
|
100396
100568
|
init_Colormaps();
|
|
100397
100569
|
init_MineRenderData();
|
|
100398
100570
|
var BlockTints = class {
|
|
100399
|
-
/**
|
|
100400
|
-
static async
|
|
100571
|
+
/** Returns a block's versioned biome color source, leaving fixed-color blocks unchanged. */
|
|
100572
|
+
static async biomeSource(key) {
|
|
100573
|
+
const rule = key && (await MineRenderData.get("blockTints", key.root))[key.toNamespacedString()];
|
|
100574
|
+
return rule ? rule.biome ?? (rule.source === "grass" ? "grass" : void 0) : void 0;
|
|
100575
|
+
}
|
|
100576
|
+
/** Resolves one block's biome tint at world block coordinates, without biome blending. */
|
|
100577
|
+
static async getBiomeColor(key, biome, position) {
|
|
100578
|
+
if (!biome) return void 0;
|
|
100579
|
+
const x4 = position?.[0], z4 = position?.[2];
|
|
100580
|
+
const source = await this.biomeSource(key);
|
|
100581
|
+
return source ? Biomes.getColor(biome, source, key, x4, z4) : void 0;
|
|
100582
|
+
}
|
|
100583
|
+
/** Resolves used tint indices from biome or preview colors; explicit tints take precedence. */
|
|
100584
|
+
static async get(key, state, model, tints, biomeColor) {
|
|
100401
100585
|
if (!key) return tints;
|
|
100402
100586
|
const candidates = (model.elements ?? []).flatMap((element) => Object.values(element.faces)).some((face) => face?.tintindex !== void 0 && face.tintindex >= 0 && tints?.[face.tintindex] === void 0);
|
|
100403
100587
|
if (!candidates) return tints;
|
|
@@ -100413,8 +100597,12 @@ property list uchar int vertex_index
|
|
|
100413
100597
|
}
|
|
100414
100598
|
}
|
|
100415
100599
|
if (!indices.size) return tints;
|
|
100600
|
+
const source = rule.biome ?? (rule.source === "grass" ? "grass" : void 0);
|
|
100601
|
+
const biome = source ? typeof biomeColor === "function" ? await biomeColor() : biomeColor : void 0;
|
|
100416
100602
|
let color3;
|
|
100417
|
-
|
|
100603
|
+
if (biome !== void 0) {
|
|
100604
|
+
color3 = biome;
|
|
100605
|
+
} else switch (rule.source) {
|
|
100418
100606
|
case "constant":
|
|
100419
100607
|
color3 = rule.color;
|
|
100420
100608
|
break;
|
|
@@ -100481,6 +100669,7 @@ property list uchar int vertex_index
|
|
|
100481
100669
|
this._entityGeneration = 0;
|
|
100482
100670
|
this.options = (0, import_ts_deepmerge6.default)({}, _BlockObject.DEFAULT_OPTIONS, options ?? {});
|
|
100483
100671
|
this.variantPosition = options?.variantPosition ? [...options.variantPosition] : void 0;
|
|
100672
|
+
this.biomePosition = options?.biomePosition ? [...options.biomePosition] : void 0;
|
|
100484
100673
|
}
|
|
100485
100674
|
async init() {
|
|
100486
100675
|
const root = AssetLoader.ROOT, scope = AssetLoader.persistentScope;
|
|
@@ -100673,11 +100862,16 @@ property list uchar int vertex_index
|
|
|
100673
100862
|
const { FluidModelObject: FluidModelObject2, sampleFluid: sampleFluid2 } = await Promise.resolve().then(() => (init_FluidModelObject(), FluidModelObject_exports));
|
|
100674
100863
|
this._fluidSampler = sample;
|
|
100675
100864
|
const surface = sampleFluid2(kind, (x4, y5, z4) => x4 === 0 && y5 === 0 && z4 === 0 ? { fluid: kind, level: this.fluidLevel } : sample?.(x4, y5, z4) ?? {});
|
|
100676
|
-
|
|
100865
|
+
const tint = this.options.tints?.[0] ?? this.waterTint;
|
|
100866
|
+
const fluidKey = `${surface.key}|${tint ?? "default"}`;
|
|
100867
|
+
if (this._fluidKey === fluidKey) return;
|
|
100677
100868
|
const key = new AssetKey("minecraft", `${kind}/${surface.key}`, "models", "fluid", "assets", ".json", this.blockState.key?.root);
|
|
100678
100869
|
const replacement = await this.scene.addSceneObject(
|
|
100679
100870
|
{ key },
|
|
100680
|
-
() => new FluidModelObject2(kind, surface.sample, this.blockState.key,
|
|
100871
|
+
() => new FluidModelObject2(kind, surface.sample, this.blockState.key, {
|
|
100872
|
+
...this.options,
|
|
100873
|
+
tints: tint === void 0 ? this.options.tints : { ...this.options.tints, 0: tint }
|
|
100874
|
+
})
|
|
100681
100875
|
);
|
|
100682
100876
|
const previous = this._fluidModel;
|
|
100683
100877
|
const matrix = previous ? this.getModelMatrix(previous) : new Matrix4().makeTranslation(...this.position.toArray());
|
|
@@ -100686,7 +100880,7 @@ property list uchar int vertex_index
|
|
|
100686
100880
|
this._models = this._models.filter((model) => model !== previous);
|
|
100687
100881
|
this._models.push(replacement);
|
|
100688
100882
|
this._fluidModel = replacement;
|
|
100689
|
-
this._fluidKey =
|
|
100883
|
+
this._fluidKey = fluidKey;
|
|
100690
100884
|
this._isInstanced || (this._isInstanced = isInstanceReference(replacement));
|
|
100691
100885
|
this._instanceCounter = this._isInstanced ? 1 : 0;
|
|
100692
100886
|
if (previous) this.removeModels([previous]);
|
|
@@ -100709,6 +100903,7 @@ property list uchar int vertex_index
|
|
|
100709
100903
|
}
|
|
100710
100904
|
async recreateModels() {
|
|
100711
100905
|
this.clearModels();
|
|
100906
|
+
this.waterTint = this.fluidKind === "water" && this.options.biome && this.options.tints?.[0] === void 0 ? await Biomes.getColor(this.options.biome, "water", this.blockState.key) : void 0;
|
|
100712
100907
|
if (resolveBlockFluidState(this.blockState.key, this.state, this._fluidRules)?.renderModel === false) {
|
|
100713
100908
|
await this.updateFluid(this._fluidSampler);
|
|
100714
100909
|
return;
|
|
@@ -100743,7 +100938,13 @@ property list uchar int vertex_index
|
|
|
100743
100938
|
const model = await Models.getMerged(modelKey);
|
|
100744
100939
|
const options = {
|
|
100745
100940
|
...this.options,
|
|
100746
|
-
tints: model ? await BlockTints.get(
|
|
100941
|
+
tints: model ? await BlockTints.get(
|
|
100942
|
+
this.blockState.key,
|
|
100943
|
+
this.state,
|
|
100944
|
+
model,
|
|
100945
|
+
this.options.tints,
|
|
100946
|
+
() => BlockTints.getBiomeColor(this.blockState.key, this.options.biome, this.biomePosition)
|
|
100947
|
+
) : this.options.tints,
|
|
100747
100948
|
uvLockRotation: variant.uvlock && (rotation.x !== 0 || rotation.y !== 0) ? [rotation.x, rotation.y, rotation.z] : void 0,
|
|
100748
100949
|
cullMask: this.options.displayPosition ? 0 : ModelCulling.toLocalMask(this._cullMask, rotation)
|
|
100749
100950
|
};
|
|
@@ -101366,6 +101567,324 @@ property list uchar int vertex_index
|
|
|
101366
101567
|
init_buffer2();
|
|
101367
101568
|
init_process2();
|
|
101368
101569
|
|
|
101570
|
+
// src/renderer/FlyControls.ts
|
|
101571
|
+
init_dirname();
|
|
101572
|
+
init_buffer2();
|
|
101573
|
+
init_process2();
|
|
101574
|
+
init_three_module();
|
|
101575
|
+
var VANILLA_FLY_SPEED = 10.89;
|
|
101576
|
+
var PITCH_LIMIT = Math.PI / 2;
|
|
101577
|
+
var MOVE_EPSILON = 1e-6;
|
|
101578
|
+
var _euler = new Euler(0, 0, 0, "YXZ");
|
|
101579
|
+
var _forward = new Vector3();
|
|
101580
|
+
var _right = new Vector3();
|
|
101581
|
+
var _targetVelocity = new Vector3();
|
|
101582
|
+
var FlyControls = class extends Controls {
|
|
101583
|
+
constructor(camera, domElement) {
|
|
101584
|
+
super(camera, domElement ?? null);
|
|
101585
|
+
this.isFlyControls = true;
|
|
101586
|
+
/** Horizontal and vertical speed in scene units per second; vanilla creative flight by default. */
|
|
101587
|
+
this.movementSpeed = 16 * VANILLA_FLY_SPEED;
|
|
101588
|
+
/** Speed multiplier while the sprint key is held. */
|
|
101589
|
+
this.sprintMultiplier = 2;
|
|
101590
|
+
/** Radians per pixel of pointer movement. */
|
|
101591
|
+
this.lookSpeed = 2e-3;
|
|
101592
|
+
/** Smooth acceleration and deceleration, approximating vanilla flight momentum. */
|
|
101593
|
+
this.enableDamping = true;
|
|
101594
|
+
/** Portion of the remaining velocity change applied per 60 Hz frame (0–1) when damping is enabled. */
|
|
101595
|
+
this.dampingFactor = 0.25;
|
|
101596
|
+
/** Capture the pointer on click so the mouse turns the camera without dragging; dragging works regardless. */
|
|
101597
|
+
this.pointerLock = true;
|
|
101598
|
+
/** Scroll the wheel to change `movementSpeed` within `speedRange`. */
|
|
101599
|
+
this.enableWheelSpeed = true;
|
|
101600
|
+
/** Minimum and maximum `movementSpeed` reachable with the wheel. */
|
|
101601
|
+
this.speedRange = [16, 16 * 500];
|
|
101602
|
+
/** Touch joystick travel in CSS pixels for full speed. */
|
|
101603
|
+
this.joystickRadius = 64;
|
|
101604
|
+
/** Key bindings by `KeyboardEvent.code`. */
|
|
101605
|
+
this.keys = {
|
|
101606
|
+
forward: ["KeyW", "ArrowUp"],
|
|
101607
|
+
back: ["KeyS", "ArrowDown"],
|
|
101608
|
+
left: ["KeyA", "ArrowLeft"],
|
|
101609
|
+
right: ["KeyD", "ArrowRight"],
|
|
101610
|
+
up: ["Space"],
|
|
101611
|
+
down: ["ShiftLeft", "ShiftRight"],
|
|
101612
|
+
sprint: ["ControlLeft", "ControlRight"]
|
|
101613
|
+
};
|
|
101614
|
+
this._pressed = /* @__PURE__ */ new Set();
|
|
101615
|
+
this._velocity = new Vector3();
|
|
101616
|
+
this._lastPosition = new Vector3();
|
|
101617
|
+
this._lastQuaternion = new Quaternion();
|
|
101618
|
+
this._position0 = new Vector3();
|
|
101619
|
+
this._quaternion0 = new Quaternion();
|
|
101620
|
+
this._dragMoved = false;
|
|
101621
|
+
this._locked = false;
|
|
101622
|
+
this._onKeyDown = (event) => this.handleKey(event, true);
|
|
101623
|
+
this._onKeyUp = (event) => this.handleKey(event, false);
|
|
101624
|
+
this._onPointerDown = (event) => this.handlePointerDown(event);
|
|
101625
|
+
this._onPointerMove = (event) => this.handlePointerMove(event);
|
|
101626
|
+
this._onPointerUp = (event) => this.handlePointerUp(event);
|
|
101627
|
+
this._onPointerLockChange = () => this.handlePointerLockChange();
|
|
101628
|
+
this._onContextMenu = (event) => event.preventDefault();
|
|
101629
|
+
this._onWheel = (event) => this.handleWheel(event);
|
|
101630
|
+
this._onBlur = () => this.releaseKeys();
|
|
101631
|
+
this._lastPosition.copy(camera.position);
|
|
101632
|
+
this._lastQuaternion.copy(camera.quaternion);
|
|
101633
|
+
this.saveState();
|
|
101634
|
+
if (domElement) this.connect(domElement);
|
|
101635
|
+
}
|
|
101636
|
+
connect(element) {
|
|
101637
|
+
super.connect(element);
|
|
101638
|
+
const document2 = element.ownerDocument;
|
|
101639
|
+
document2.addEventListener("keydown", this._onKeyDown);
|
|
101640
|
+
document2.addEventListener("keyup", this._onKeyUp);
|
|
101641
|
+
document2.addEventListener("pointerlockchange", this._onPointerLockChange);
|
|
101642
|
+
document2.defaultView?.addEventListener("blur", this._onBlur);
|
|
101643
|
+
element.addEventListener("pointerdown", this._onPointerDown);
|
|
101644
|
+
element.addEventListener("pointermove", this._onPointerMove);
|
|
101645
|
+
element.addEventListener("pointerup", this._onPointerUp);
|
|
101646
|
+
element.addEventListener("pointercancel", this._onPointerUp);
|
|
101647
|
+
element.addEventListener("contextmenu", this._onContextMenu);
|
|
101648
|
+
element.addEventListener("wheel", this._onWheel, { passive: false });
|
|
101649
|
+
element.addEventListener("blur", this._onBlur);
|
|
101650
|
+
element.style.touchAction = "none";
|
|
101651
|
+
if (element.tabIndex < 0) element.tabIndex = 0;
|
|
101652
|
+
}
|
|
101653
|
+
disconnect() {
|
|
101654
|
+
const element = this.domElement;
|
|
101655
|
+
if (!element) return;
|
|
101656
|
+
const document2 = element.ownerDocument;
|
|
101657
|
+
document2.removeEventListener("keydown", this._onKeyDown);
|
|
101658
|
+
document2.removeEventListener("keyup", this._onKeyUp);
|
|
101659
|
+
document2.removeEventListener("pointerlockchange", this._onPointerLockChange);
|
|
101660
|
+
document2.defaultView?.removeEventListener("blur", this._onBlur);
|
|
101661
|
+
element.removeEventListener("pointerdown", this._onPointerDown);
|
|
101662
|
+
element.removeEventListener("pointermove", this._onPointerMove);
|
|
101663
|
+
element.removeEventListener("pointerup", this._onPointerUp);
|
|
101664
|
+
element.removeEventListener("pointercancel", this._onPointerUp);
|
|
101665
|
+
element.removeEventListener("contextmenu", this._onContextMenu);
|
|
101666
|
+
element.removeEventListener("wheel", this._onWheel);
|
|
101667
|
+
element.removeEventListener("blur", this._onBlur);
|
|
101668
|
+
element.style.touchAction = "auto";
|
|
101669
|
+
this.unlock();
|
|
101670
|
+
this._locked = false;
|
|
101671
|
+
this.releaseKeys();
|
|
101672
|
+
this._dragPointer = void 0;
|
|
101673
|
+
this._joystick = void 0;
|
|
101674
|
+
}
|
|
101675
|
+
dispose() {
|
|
101676
|
+
this.disconnect();
|
|
101677
|
+
}
|
|
101678
|
+
/** Whether mouse look currently owns the pointer. */
|
|
101679
|
+
get locked() {
|
|
101680
|
+
return this._locked;
|
|
101681
|
+
}
|
|
101682
|
+
/** Requests pointer capture; browsers only allow this from a user gesture. */
|
|
101683
|
+
lock() {
|
|
101684
|
+
const element = this.domElement;
|
|
101685
|
+
if (!element || this._locked || typeof element.requestPointerLock !== "function") return;
|
|
101686
|
+
try {
|
|
101687
|
+
const result = element.requestPointerLock();
|
|
101688
|
+
if (result instanceof Promise) result.catch(() => void 0);
|
|
101689
|
+
} catch {
|
|
101690
|
+
}
|
|
101691
|
+
}
|
|
101692
|
+
/** Releases a captured pointer. */
|
|
101693
|
+
unlock() {
|
|
101694
|
+
const document2 = this.domElement?.ownerDocument;
|
|
101695
|
+
if (document2?.pointerLockElement && document2.pointerLockElement === this.domElement) {
|
|
101696
|
+
document2.exitPointerLock();
|
|
101697
|
+
}
|
|
101698
|
+
}
|
|
101699
|
+
/** Stores the camera pose that {@link reset} restores. */
|
|
101700
|
+
saveState() {
|
|
101701
|
+
this._position0.copy(this.object.position);
|
|
101702
|
+
this._quaternion0.copy(this.object.quaternion);
|
|
101703
|
+
}
|
|
101704
|
+
/** Restores the saved camera pose and stops movement. */
|
|
101705
|
+
reset() {
|
|
101706
|
+
this.object.position.copy(this._position0);
|
|
101707
|
+
this.object.quaternion.copy(this._quaternion0);
|
|
101708
|
+
this._velocity.set(0, 0, 0);
|
|
101709
|
+
this.notifyChange();
|
|
101710
|
+
}
|
|
101711
|
+
/** Horizontal yaw in radians, where zero looks toward -Z. */
|
|
101712
|
+
get yaw() {
|
|
101713
|
+
return _euler.setFromQuaternion(this.object.quaternion).y;
|
|
101714
|
+
}
|
|
101715
|
+
/** Vertical pitch in radians, positive looking up. */
|
|
101716
|
+
get pitch() {
|
|
101717
|
+
return _euler.setFromQuaternion(this.object.quaternion).x;
|
|
101718
|
+
}
|
|
101719
|
+
/** Turns the camera; pitch is clamped to straight up and down. */
|
|
101720
|
+
setRotation(yaw, pitch) {
|
|
101721
|
+
_euler.set(MathUtils.clamp(pitch, -PITCH_LIMIT, PITCH_LIMIT), yaw, 0);
|
|
101722
|
+
this.object.quaternion.setFromEuler(_euler);
|
|
101723
|
+
this.notifyChange();
|
|
101724
|
+
}
|
|
101725
|
+
/** Points the camera at a position without rolling it. */
|
|
101726
|
+
lookAt(target) {
|
|
101727
|
+
_forward.copy(target).sub(this.object.position);
|
|
101728
|
+
if (_forward.lengthSq() < MOVE_EPSILON) return;
|
|
101729
|
+
_forward.normalize();
|
|
101730
|
+
this.setRotation(Math.atan2(-_forward.x, -_forward.z), Math.asin(MathUtils.clamp(_forward.y, -1, 1)));
|
|
101731
|
+
}
|
|
101732
|
+
/** Whether an action's key is held. */
|
|
101733
|
+
isPressed(action) {
|
|
101734
|
+
return this._pressed.has(action);
|
|
101735
|
+
}
|
|
101736
|
+
/**
|
|
101737
|
+
* Advances movement by `delta` seconds (measured since the previous call when omitted)
|
|
101738
|
+
* and dispatches `change` when the camera moved.
|
|
101739
|
+
*/
|
|
101740
|
+
update(delta) {
|
|
101741
|
+
if (delta === void 0) {
|
|
101742
|
+
const now = typeof performance !== "undefined" ? performance.now() : Date.now();
|
|
101743
|
+
delta = this._lastTime === void 0 ? 0 : (now - this._lastTime) / 1e3;
|
|
101744
|
+
this._lastTime = now;
|
|
101745
|
+
}
|
|
101746
|
+
if (!this.enabled) {
|
|
101747
|
+
this._velocity.set(0, 0, 0);
|
|
101748
|
+
return;
|
|
101749
|
+
}
|
|
101750
|
+
if (delta > 0) this.move(delta);
|
|
101751
|
+
this.notifyChange();
|
|
101752
|
+
}
|
|
101753
|
+
move(delta) {
|
|
101754
|
+
const camera = this.object;
|
|
101755
|
+
let forward = (this._pressed.has("forward") ? 1 : 0) - (this._pressed.has("back") ? 1 : 0);
|
|
101756
|
+
let strafe = (this._pressed.has("right") ? 1 : 0) - (this._pressed.has("left") ? 1 : 0);
|
|
101757
|
+
const climb = (this._pressed.has("up") ? 1 : 0) - (this._pressed.has("down") ? 1 : 0);
|
|
101758
|
+
const joystick = this._joystick;
|
|
101759
|
+
if (joystick) {
|
|
101760
|
+
const radius = Math.max(this.joystickRadius, 1);
|
|
101761
|
+
forward = MathUtils.clamp(forward + (joystick.originY - joystick.y) / radius, -1, 1);
|
|
101762
|
+
strafe = MathUtils.clamp(strafe + (joystick.x - joystick.originX) / radius, -1, 1);
|
|
101763
|
+
}
|
|
101764
|
+
_euler.setFromQuaternion(camera.quaternion);
|
|
101765
|
+
const yaw = _euler.y;
|
|
101766
|
+
_forward.set(-Math.sin(yaw), 0, -Math.cos(yaw));
|
|
101767
|
+
_right.set(Math.cos(yaw), 0, -Math.sin(yaw));
|
|
101768
|
+
_targetVelocity.set(0, 0, 0);
|
|
101769
|
+
if (forward || strafe || climb) {
|
|
101770
|
+
_targetVelocity.addScaledVector(_forward, forward).addScaledVector(_right, strafe);
|
|
101771
|
+
if (_targetVelocity.lengthSq() > 1) _targetVelocity.normalize();
|
|
101772
|
+
_targetVelocity.y = climb;
|
|
101773
|
+
const speed = this.movementSpeed * (this._pressed.has("sprint") ? this.sprintMultiplier : 1);
|
|
101774
|
+
_targetVelocity.multiplyScalar(speed);
|
|
101775
|
+
}
|
|
101776
|
+
if (this.enableDamping) {
|
|
101777
|
+
const blend = 1 - Math.pow(1 - MathUtils.clamp(this.dampingFactor, 0, 1), delta * 60);
|
|
101778
|
+
this._velocity.lerp(_targetVelocity, blend);
|
|
101779
|
+
if (_targetVelocity.lengthSq() === 0 && this._velocity.lengthSq() < MOVE_EPSILON) this._velocity.set(0, 0, 0);
|
|
101780
|
+
} else {
|
|
101781
|
+
this._velocity.copy(_targetVelocity);
|
|
101782
|
+
}
|
|
101783
|
+
camera.position.addScaledVector(this._velocity, delta);
|
|
101784
|
+
}
|
|
101785
|
+
notifyChange() {
|
|
101786
|
+
const camera = this.object;
|
|
101787
|
+
if (this._lastPosition.distanceToSquared(camera.position) > MOVE_EPSILON || 8 * (1 - this._lastQuaternion.dot(camera.quaternion)) > MOVE_EPSILON) {
|
|
101788
|
+
this._lastPosition.copy(camera.position);
|
|
101789
|
+
this._lastQuaternion.copy(camera.quaternion);
|
|
101790
|
+
this.dispatchEvent({ type: "change" });
|
|
101791
|
+
}
|
|
101792
|
+
}
|
|
101793
|
+
releaseKeys() {
|
|
101794
|
+
this._pressed.clear();
|
|
101795
|
+
}
|
|
101796
|
+
handleKey(event, down) {
|
|
101797
|
+
const action = this.actionFor(event.code);
|
|
101798
|
+
if (!action) return;
|
|
101799
|
+
const ownsInput = this.enabled && (this._locked || event.target === this.domElement);
|
|
101800
|
+
if (down && !ownsInput) return;
|
|
101801
|
+
const pressed = this._pressed.has(action);
|
|
101802
|
+
if (down) this._pressed.add(action);
|
|
101803
|
+
else this._pressed.delete(action);
|
|
101804
|
+
if (ownsInput || this.enabled && pressed) event.preventDefault();
|
|
101805
|
+
}
|
|
101806
|
+
actionFor(code2) {
|
|
101807
|
+
for (const action in this.keys) {
|
|
101808
|
+
if (this.keys[action].includes(code2)) return action;
|
|
101809
|
+
}
|
|
101810
|
+
return void 0;
|
|
101811
|
+
}
|
|
101812
|
+
handlePointerDown(event) {
|
|
101813
|
+
const element = this.domElement;
|
|
101814
|
+
if (!this.enabled || !element) return;
|
|
101815
|
+
element.focus?.({ preventScroll: true });
|
|
101816
|
+
if (this._locked) return;
|
|
101817
|
+
if (event.pointerType === "touch" && !this._joystick && this.onJoystickSide(event)) {
|
|
101818
|
+
this._joystick = { id: event.pointerId, originX: event.clientX, originY: event.clientY, x: event.clientX, y: event.clientY };
|
|
101819
|
+
element.setPointerCapture?.(event.pointerId);
|
|
101820
|
+
return;
|
|
101821
|
+
}
|
|
101822
|
+
if (this._dragPointer !== void 0) return;
|
|
101823
|
+
if (event.pointerType === "mouse" && event.button !== 0 && event.button !== 2) return;
|
|
101824
|
+
this._dragPointer = event.pointerId;
|
|
101825
|
+
this._dragMoved = false;
|
|
101826
|
+
element.setPointerCapture?.(event.pointerId);
|
|
101827
|
+
}
|
|
101828
|
+
onJoystickSide(event) {
|
|
101829
|
+
const rect = this.domElement?.getBoundingClientRect?.();
|
|
101830
|
+
return !!rect && event.clientX < rect.left + rect.width / 2;
|
|
101831
|
+
}
|
|
101832
|
+
handlePointerMove(event) {
|
|
101833
|
+
if (!this.enabled) return;
|
|
101834
|
+
const joystick = this._joystick;
|
|
101835
|
+
if (joystick && event.pointerId === joystick.id) {
|
|
101836
|
+
joystick.x = event.clientX;
|
|
101837
|
+
joystick.y = event.clientY;
|
|
101838
|
+
return;
|
|
101839
|
+
}
|
|
101840
|
+
if (!this._locked && event.pointerId !== this._dragPointer) return;
|
|
101841
|
+
const dx = event.movementX ?? 0;
|
|
101842
|
+
const dy = event.movementY ?? 0;
|
|
101843
|
+
if (!dx && !dy) return;
|
|
101844
|
+
this._dragMoved = true;
|
|
101845
|
+
this.turn(dx, dy);
|
|
101846
|
+
}
|
|
101847
|
+
handlePointerUp(event) {
|
|
101848
|
+
if (this._joystick?.id === event.pointerId) {
|
|
101849
|
+
this._joystick = void 0;
|
|
101850
|
+
this.domElement?.releasePointerCapture?.(event.pointerId);
|
|
101851
|
+
return;
|
|
101852
|
+
}
|
|
101853
|
+
if (event.pointerId !== this._dragPointer) return;
|
|
101854
|
+
this._dragPointer = void 0;
|
|
101855
|
+
this.domElement?.releasePointerCapture?.(event.pointerId);
|
|
101856
|
+
if (this.enabled && this.pointerLock && !this._dragMoved && event.pointerType === "mouse" && event.button === 0) {
|
|
101857
|
+
this.lock();
|
|
101858
|
+
}
|
|
101859
|
+
}
|
|
101860
|
+
handleWheel(event) {
|
|
101861
|
+
if (!this.enabled || !this.enableWheelSpeed) return;
|
|
101862
|
+
event.preventDefault();
|
|
101863
|
+
const steps = event.deltaMode === 0 ? event.deltaY / 100 : event.deltaY;
|
|
101864
|
+
const [min, max2] = this.speedRange;
|
|
101865
|
+
this.movementSpeed = MathUtils.clamp(this.movementSpeed * Math.pow(1.15, -steps), Math.min(min, max2), Math.max(min, max2));
|
|
101866
|
+
}
|
|
101867
|
+
handlePointerLockChange() {
|
|
101868
|
+
const document2 = this.domElement?.ownerDocument;
|
|
101869
|
+
const locked = !!document2 && document2.pointerLockElement === this.domElement;
|
|
101870
|
+
if (locked === this._locked) return;
|
|
101871
|
+
this._locked = locked;
|
|
101872
|
+
if (!locked) this.releaseKeys();
|
|
101873
|
+
this.dispatchEvent({ type: locked ? "lock" : "unlock" });
|
|
101874
|
+
}
|
|
101875
|
+
turn(dx, dy) {
|
|
101876
|
+
_euler.setFromQuaternion(this.object.quaternion);
|
|
101877
|
+
_euler.y -= dx * this.lookSpeed;
|
|
101878
|
+
_euler.x = MathUtils.clamp(_euler.x - dy * this.lookSpeed, -PITCH_LIMIT, PITCH_LIMIT);
|
|
101879
|
+
_euler.z = 0;
|
|
101880
|
+
this.object.quaternion.setFromEuler(_euler);
|
|
101881
|
+
this.notifyChange();
|
|
101882
|
+
}
|
|
101883
|
+
};
|
|
101884
|
+
function isFlyControls(obj) {
|
|
101885
|
+
return obj?.isFlyControls === true;
|
|
101886
|
+
}
|
|
101887
|
+
|
|
101369
101888
|
// src/renderer/MineRenderScene.ts
|
|
101370
101889
|
init_dirname();
|
|
101371
101890
|
init_buffer2();
|
|
@@ -105204,20 +105723,77 @@ gl_FragDepth=readDepth(vUv);
|
|
|
105204
105723
|
}
|
|
105205
105724
|
createControls() {
|
|
105206
105725
|
if (!this.options.controls?.enabled) return void 0;
|
|
105207
|
-
|
|
105208
|
-
|
|
105209
|
-
|
|
105726
|
+
return this.createControlsFor(this.options.controls.mode ?? "orbit", this.initialTarget());
|
|
105727
|
+
}
|
|
105728
|
+
initialTarget() {
|
|
105210
105729
|
const target = this.options.camera.lookingAt;
|
|
105211
|
-
if (isVector3(target))
|
|
105730
|
+
if (isVector3(target)) return target.clone();
|
|
105731
|
+
if (isTripleArray(target)) return new Vector3(target[0], target[1], target[2]);
|
|
105732
|
+
return new Vector3();
|
|
105733
|
+
}
|
|
105734
|
+
createControlsFor(mode2, target) {
|
|
105735
|
+
let controls;
|
|
105736
|
+
if (mode2 === "fly") {
|
|
105737
|
+
controls = new FlyControls(this.camera, this.renderer.domElement);
|
|
105738
|
+
controls.lookAt(target);
|
|
105739
|
+
controls.saveState();
|
|
105740
|
+
} else {
|
|
105741
|
+
const position = this.camera.position.clone();
|
|
105742
|
+
controls = new OrbitControls(this.camera, this.renderer.domElement);
|
|
105743
|
+
this.camera.position.copy(position);
|
|
105212
105744
|
controls.target.copy(target);
|
|
105213
|
-
|
|
105214
|
-
controls.
|
|
105745
|
+
controls.update();
|
|
105746
|
+
controls.saveState();
|
|
105215
105747
|
}
|
|
105216
|
-
|
|
105217
|
-
controls.saveState();
|
|
105748
|
+
this._controlsTime = void 0;
|
|
105218
105749
|
this.registerEventDispatcher(controls);
|
|
105219
105750
|
return controls;
|
|
105220
105751
|
}
|
|
105752
|
+
/**
|
|
105753
|
+
* Replaces renderer-owned controls with the selected mode, keeping the camera where it is.
|
|
105754
|
+
* Switching to orbit controls targets the point the camera looks at, at the previous orbit distance.
|
|
105755
|
+
* Returns the new controls, or undefined when controls were disabled at construction or after disposal.
|
|
105756
|
+
*/
|
|
105757
|
+
setControlsMode(mode2) {
|
|
105758
|
+
const current = this._controls;
|
|
105759
|
+
if (this._disposed || !current) return void 0;
|
|
105760
|
+
if (this.controlsMode === mode2) return current;
|
|
105761
|
+
let target;
|
|
105762
|
+
if (isFlyControls(current)) {
|
|
105763
|
+
const distance = this._orbitDistance ?? (this.camera.position.distanceTo(this.initialTarget()) || 1);
|
|
105764
|
+
target = new Vector3(0, 0, -distance).applyQuaternion(this.camera.quaternion).add(this.camera.position);
|
|
105765
|
+
} else {
|
|
105766
|
+
target = current.target.clone();
|
|
105767
|
+
this._orbitDistance = this.camera.position.distanceTo(target);
|
|
105768
|
+
}
|
|
105769
|
+
const enabled = current.enabled;
|
|
105770
|
+
this.disposeControls(current);
|
|
105771
|
+
this._controls = this.createControlsFor(mode2, target);
|
|
105772
|
+
this._controls.enabled = enabled;
|
|
105773
|
+
this.dirty = true;
|
|
105774
|
+
return this._controls;
|
|
105775
|
+
}
|
|
105776
|
+
disposeControls(controls) {
|
|
105777
|
+
this._controls = void 0;
|
|
105778
|
+
this.unregisterEventDispatcher(controls);
|
|
105779
|
+
controls.enabled = false;
|
|
105780
|
+
controls.dispose();
|
|
105781
|
+
}
|
|
105782
|
+
/** Advances owned controls; without a frame time, flight movement does not progress. */
|
|
105783
|
+
updateControls(time) {
|
|
105784
|
+
const controls = this._controls;
|
|
105785
|
+
if (!controls?.enabled) {
|
|
105786
|
+
this._controlsTime = void 0;
|
|
105787
|
+
return;
|
|
105788
|
+
}
|
|
105789
|
+
if (!isFlyControls(controls)) {
|
|
105790
|
+
controls.update();
|
|
105791
|
+
return;
|
|
105792
|
+
}
|
|
105793
|
+
const previous = this._controlsTime;
|
|
105794
|
+
if (time !== void 0) this._controlsTime = time;
|
|
105795
|
+
controls.update(time === void 0 || previous === void 0 ? 0 : (time - previous) / 1e3);
|
|
105796
|
+
}
|
|
105221
105797
|
//</editor-fold>
|
|
105222
105798
|
init() {
|
|
105223
105799
|
if (this._disposed) return;
|
|
@@ -105294,6 +105870,12 @@ gl_FragDepth=readDepth(vUv);
|
|
|
105294
105870
|
events.add(changeEvent2);
|
|
105295
105871
|
dispatcher.addEventListener(changeEvent2, this._changeListener);
|
|
105296
105872
|
}
|
|
105873
|
+
unregisterEventDispatcher(dispatcher) {
|
|
105874
|
+
const events = this._eventDispatchers.get(dispatcher);
|
|
105875
|
+
if (!events) return;
|
|
105876
|
+
for (const event of events) dispatcher.removeEventListener(event, this._changeListener);
|
|
105877
|
+
this._eventDispatchers.delete(dispatcher);
|
|
105878
|
+
}
|
|
105297
105879
|
/** Updates the camera and canvas size. Width and height are in CSS pixels. */
|
|
105298
105880
|
resize(width, height) {
|
|
105299
105881
|
if (this._disposed) return;
|
|
@@ -105370,6 +105952,7 @@ gl_FragDepth=readDepth(vUv);
|
|
|
105370
105952
|
this.renderer.setAnimationLoop(null);
|
|
105371
105953
|
}
|
|
105372
105954
|
this._nextFrameTime = void 0;
|
|
105955
|
+
this._controlsTime = void 0;
|
|
105373
105956
|
for (const subscription of this._frameCallbacks.values()) subscription.previous = void 0;
|
|
105374
105957
|
}
|
|
105375
105958
|
/**
|
|
@@ -105399,10 +105982,7 @@ gl_FragDepth=readDepth(vUv);
|
|
|
105399
105982
|
}
|
|
105400
105983
|
this._element = void 0;
|
|
105401
105984
|
if (this._controls) {
|
|
105402
|
-
|
|
105403
|
-
this._controls = void 0;
|
|
105404
|
-
controls.enabled = false;
|
|
105405
|
-
controls.dispose();
|
|
105985
|
+
this.disposeControls(this._controls);
|
|
105406
105986
|
}
|
|
105407
105987
|
this.scene.clear();
|
|
105408
105988
|
for (const helper of this._debugHelpers) {
|
|
@@ -105419,9 +105999,7 @@ gl_FragDepth=readDepth(vUv);
|
|
|
105419
105999
|
}
|
|
105420
106000
|
animate(t5 = performance.now()) {
|
|
105421
106001
|
if (!this._running) return;
|
|
105422
|
-
|
|
105423
|
-
this._controls.update();
|
|
105424
|
-
}
|
|
106002
|
+
this.updateControls(t5);
|
|
105425
106003
|
if (!this._running) return;
|
|
105426
106004
|
if (!this.dirty && !this.options.render.renderAlways && !this._frameCallbacks.size && !this._videoExporter) return;
|
|
105427
106005
|
const interval = this._frameInterval;
|
|
@@ -105458,7 +106036,7 @@ gl_FragDepth=readDepth(vUv);
|
|
|
105458
106036
|
/** Draws a fresh frame without starting the animation loop or invoking frame callbacks. */
|
|
105459
106037
|
renderOnce() {
|
|
105460
106038
|
if (this._disposed) throw new Error("Cannot render a disposed renderer");
|
|
105461
|
-
|
|
106039
|
+
this.updateControls();
|
|
105462
106040
|
this.drawFrame();
|
|
105463
106041
|
}
|
|
105464
106042
|
/**
|
|
@@ -105488,7 +106066,7 @@ gl_FragDepth=readDepth(vUv);
|
|
|
105488
106066
|
try {
|
|
105489
106067
|
if (!wasRunning) this.start();
|
|
105490
106068
|
this._videoExporter = exporter;
|
|
105491
|
-
|
|
106069
|
+
this.updateControls();
|
|
105492
106070
|
this.drawFrame();
|
|
105493
106071
|
} catch (error2) {
|
|
105494
106072
|
exporter.cancel(error2);
|
|
@@ -105539,6 +106117,19 @@ gl_FragDepth=readDepth(vUv);
|
|
|
105539
106117
|
get controls() {
|
|
105540
106118
|
return this._controls;
|
|
105541
106119
|
}
|
|
106120
|
+
/** Renderer-owned OrbitControls, or undefined in fly mode or without controls. */
|
|
106121
|
+
get orbitControls() {
|
|
106122
|
+
return this._controls && !isFlyControls(this._controls) ? this._controls : void 0;
|
|
106123
|
+
}
|
|
106124
|
+
/** Renderer-owned {@link FlyControls}, or undefined in orbit mode or without controls. */
|
|
106125
|
+
get flyControls() {
|
|
106126
|
+
return isFlyControls(this._controls) ? this._controls : void 0;
|
|
106127
|
+
}
|
|
106128
|
+
/** The active renderer-owned controls mode, or undefined without controls. */
|
|
106129
|
+
get controlsMode() {
|
|
106130
|
+
if (!this._controls) return void 0;
|
|
106131
|
+
return isFlyControls(this._controls) ? "fly" : "orbit";
|
|
106132
|
+
}
|
|
105542
106133
|
///
|
|
105543
106134
|
};
|
|
105544
106135
|
_Renderer.DEFAULT_OPTIONS = (0, import_ts_deepmerge9.default)({}, {
|
|
@@ -105572,7 +106163,8 @@ gl_FragDepth=readDepth(vUv);
|
|
|
105572
106163
|
enabled: true
|
|
105573
106164
|
},
|
|
105574
106165
|
controls: {
|
|
105575
|
-
enabled: false
|
|
106166
|
+
enabled: false,
|
|
106167
|
+
mode: "orbit"
|
|
105576
106168
|
},
|
|
105577
106169
|
debug: {
|
|
105578
106170
|
grid: false,
|
|
@@ -106936,24 +107528,48 @@ gl_FragDepth=readDepth(vUv);
|
|
|
106936
107528
|
if (!Number.isInteger(maxAtlasSize) || maxAtlasSize < 1) throw new RangeError("maxAtlasSize must be a positive integer");
|
|
106937
107529
|
}
|
|
106938
107530
|
/** Returns templates for the matched parts, or `undefined` when the block needs an individual render object. */
|
|
106939
|
-
async get(blockState3, properties = {}, position) {
|
|
106940
|
-
const
|
|
106941
|
-
|
|
107531
|
+
async get(blockState3, properties = {}, position, biome) {
|
|
107532
|
+
const biomePosition = position ? [...position] : void 0;
|
|
107533
|
+
const prepared = await this.state(blockState3, properties);
|
|
107534
|
+
if (!prepared) return void 0;
|
|
107535
|
+
return Promise.all(prepared.groups.map(async (group) => {
|
|
107536
|
+
const variant = BlockStateResolver.choose(group, biomePosition);
|
|
107537
|
+
const choice = prepared.choices.get(variant);
|
|
107538
|
+
const tints = await BlockTints.get(
|
|
107539
|
+
blockState3.key,
|
|
107540
|
+
prepared.state,
|
|
107541
|
+
choice.model,
|
|
107542
|
+
void 0,
|
|
107543
|
+
() => BlockTints.getBiomeColor(blockState3.key, biome, biomePosition)
|
|
107544
|
+
);
|
|
107545
|
+
return this.template(variant, choice, tints);
|
|
107546
|
+
}));
|
|
106942
107547
|
}
|
|
106943
|
-
/** Resolves section templates
|
|
106944
|
-
async prepareState(blockState3, properties = {}) {
|
|
107548
|
+
/** Resolves section templates for one tint palette, with a synchronous weighted choice for each cell. */
|
|
107549
|
+
async prepareState(blockState3, properties = {}, biomeColor) {
|
|
107550
|
+
const prepared = await this.state(blockState3, properties);
|
|
107551
|
+
if (!prepared) return void 0;
|
|
107552
|
+
let color3;
|
|
107553
|
+
const resolveColor = typeof biomeColor === "function" ? () => color3 ?? (color3 = biomeColor()) : biomeColor;
|
|
107554
|
+
const templates = /* @__PURE__ */ new Map();
|
|
107555
|
+
await Promise.all([...prepared.choices].map(async ([variant, choice]) => {
|
|
107556
|
+
const tints = await BlockTints.get(blockState3.key, prepared.state, choice.model, void 0, resolveColor);
|
|
107557
|
+
templates.set(variant, await this.template(variant, choice, tints));
|
|
107558
|
+
}));
|
|
107559
|
+
return { pick: (position) => prepared.groups.map((group) => templates.get(BlockStateResolver.choose(group, position))) };
|
|
107560
|
+
}
|
|
107561
|
+
async state(blockState3, properties) {
|
|
106945
107562
|
let states = this.states.get(blockState3);
|
|
106946
107563
|
if (!states) this.states.set(blockState3, states = /* @__PURE__ */ new Map());
|
|
106947
107564
|
const key = JSON.stringify(Object.entries(properties).sort(([a4], [b4]) => a4.localeCompare(b4)));
|
|
106948
|
-
|
|
106949
|
-
if (!prepared) return void 0;
|
|
106950
|
-
return { pick: (position) => prepared.groups.map((group) => prepared.templates.get(BlockStateResolver.choose(group, position))) };
|
|
107565
|
+
return cached(states, key, () => this.prepare(blockState3, properties));
|
|
106951
107566
|
}
|
|
106952
107567
|
/** Returns the shared still/flow atlas used by per-block fluid objects. */
|
|
106953
107568
|
fluidAtlas(kind, root) {
|
|
106954
|
-
|
|
107569
|
+
const key = new AssetKey("minecraft", kind, "models", "fluid", "assets", ".json", root);
|
|
107570
|
+
return cached(this.fluidAtlases, key.serialize(), async () => {
|
|
106955
107571
|
const atlas = await UVMapper.getAtlas({
|
|
106956
|
-
key
|
|
107572
|
+
key,
|
|
106957
107573
|
textures: { still: `minecraft:block/${kind}_still`, flow: `minecraft:block/${kind}_flow` },
|
|
106958
107574
|
elements: []
|
|
106959
107575
|
});
|
|
@@ -106965,64 +107581,67 @@ gl_FragDepth=readDepth(vUv);
|
|
|
106965
107581
|
const state = { ...await BlockStateResolver.defaults(blockState3), ...properties };
|
|
106966
107582
|
const groups = BlockStateResolver.matching(blockState3, state);
|
|
106967
107583
|
if (!groups.length) return void 0;
|
|
106968
|
-
const
|
|
107584
|
+
const prepared = /* @__PURE__ */ new Map();
|
|
106969
107585
|
for (const group of groups) {
|
|
106970
107586
|
const choices = Array.isArray(group) ? group : [group];
|
|
106971
107587
|
if (!choices.length) return void 0;
|
|
106972
107588
|
for (const variant of choices) {
|
|
106973
107589
|
if (!variant.model) return void 0;
|
|
106974
|
-
const
|
|
107590
|
+
const modelKey = AssetKey.parse("models", variant.model);
|
|
107591
|
+
modelKey.root = blockState3.key?.root;
|
|
107592
|
+
const model = await Models.getMerged(modelKey);
|
|
106975
107593
|
if (!model?.elements?.length) return void 0;
|
|
106976
107594
|
const atlas = await UVMapper.getAtlas(model);
|
|
106977
107595
|
const rotation = BlockStateResolver.rotation(variant);
|
|
106978
107596
|
if (!atlas || atlas.image.width > this.maxAtlasSize || atlas.image.height > this.maxAtlasSize) return void 0;
|
|
106979
|
-
|
|
106980
|
-
let models = this.models.get(model);
|
|
106981
|
-
if (!models) this.models.set(model, models = /* @__PURE__ */ new Map());
|
|
106982
|
-
const key = JSON.stringify([rotation.x, rotation.y, rotation.z, variant.uvlock, tints]);
|
|
106983
|
-
const template = await cached(models, key, async () => {
|
|
106984
|
-
const object4 = new SectionModel(model, {
|
|
106985
|
-
instanceMeshes: false,
|
|
106986
|
-
mergeMeshes: true,
|
|
106987
|
-
tints,
|
|
106988
|
-
uvLockRotation: variant.uvlock && (rotation.x !== 0 || rotation.y !== 0) ? [rotation.x, rotation.y, rotation.z] : void 0
|
|
106989
|
-
});
|
|
106990
|
-
await object4.init();
|
|
106991
|
-
let geometry = object4.children[0].geometry;
|
|
106992
|
-
geometry.applyMatrix4(new Matrix4().makeRotationFromEuler(rotation));
|
|
106993
|
-
object4.clear();
|
|
106994
|
-
const keep = [];
|
|
106995
|
-
const cullFaces = [];
|
|
106996
|
-
for (const element of atlas.model.elements) {
|
|
106997
|
-
for (const face of CUBE_FACES) {
|
|
106998
|
-
const data = element.faces[face];
|
|
106999
|
-
keep.push(data !== void 0);
|
|
107000
|
-
if (!data) continue;
|
|
107001
|
-
const local = CUBE_FACES.findIndex((name2) => name2 === data.cullface);
|
|
107002
|
-
if (local < 0) {
|
|
107003
|
-
cullFaces.push(0);
|
|
107004
|
-
continue;
|
|
107005
|
-
}
|
|
107006
|
-
const normal = new Vector3(...CUBE_FACE_OFFSETS[local]).applyEuler(rotation);
|
|
107007
|
-
const world = CUBE_FACE_OFFSETS.findIndex(([x4, y5, z4]) => Math.abs(normal.x - x4) < 1e-6 && Math.abs(normal.y - y5) < 1e-6 && Math.abs(normal.z - z4) < 1e-6);
|
|
107008
|
-
cullFaces.push(world < 0 ? 0 : 1 << world);
|
|
107009
|
-
}
|
|
107010
|
-
}
|
|
107011
|
-
geometry = compactQuads(geometry, keep);
|
|
107012
|
-
const template2 = {
|
|
107013
|
-
geometry,
|
|
107014
|
-
atlas,
|
|
107015
|
-
cullFaces: new Uint8Array(cullFaces),
|
|
107016
|
-
occludes: ModelCulling.isOpaqueFullCube(atlas) && ModelCulling.toLocalMask(63, rotation) === 63,
|
|
107017
|
-
layer: atlas.hasTranslucency ? 1 : 0
|
|
107018
|
-
};
|
|
107019
|
-
this.templates.add(template2);
|
|
107020
|
-
return template2;
|
|
107021
|
-
});
|
|
107022
|
-
templates.set(variant, template);
|
|
107597
|
+
prepared.set(variant, { model, atlas, rotation });
|
|
107023
107598
|
}
|
|
107024
107599
|
}
|
|
107025
|
-
return { groups,
|
|
107600
|
+
return { state, groups, choices: prepared };
|
|
107601
|
+
}
|
|
107602
|
+
async template(variant, { model, atlas, rotation }, tints) {
|
|
107603
|
+
let models = this.models.get(model);
|
|
107604
|
+
if (!models) this.models.set(model, models = /* @__PURE__ */ new Map());
|
|
107605
|
+
const key = JSON.stringify([rotation.x, rotation.y, rotation.z, variant.uvlock, tints]);
|
|
107606
|
+
return cached(models, key, async () => {
|
|
107607
|
+
const object4 = new SectionModel(model, {
|
|
107608
|
+
instanceMeshes: false,
|
|
107609
|
+
mergeMeshes: true,
|
|
107610
|
+
tints,
|
|
107611
|
+
uvLockRotation: variant.uvlock && (rotation.x !== 0 || rotation.y !== 0) ? [rotation.x, rotation.y, rotation.z] : void 0
|
|
107612
|
+
});
|
|
107613
|
+
await object4.init();
|
|
107614
|
+
let geometry = object4.children[0].geometry;
|
|
107615
|
+
geometry.applyMatrix4(new Matrix4().makeRotationFromEuler(rotation));
|
|
107616
|
+
object4.clear();
|
|
107617
|
+
const keep = [];
|
|
107618
|
+
const cullFaces = [];
|
|
107619
|
+
for (const element of atlas.model.elements) {
|
|
107620
|
+
for (const face of CUBE_FACES) {
|
|
107621
|
+
const data = element.faces[face];
|
|
107622
|
+
keep.push(data !== void 0);
|
|
107623
|
+
if (!data) continue;
|
|
107624
|
+
const local = CUBE_FACES.findIndex((name2) => name2 === data.cullface);
|
|
107625
|
+
if (local < 0) {
|
|
107626
|
+
cullFaces.push(0);
|
|
107627
|
+
continue;
|
|
107628
|
+
}
|
|
107629
|
+
const normal = new Vector3(...CUBE_FACE_OFFSETS[local]).applyEuler(rotation);
|
|
107630
|
+
const world = CUBE_FACE_OFFSETS.findIndex(([x4, y5, z4]) => Math.abs(normal.x - x4) < 1e-6 && Math.abs(normal.y - y5) < 1e-6 && Math.abs(normal.z - z4) < 1e-6);
|
|
107631
|
+
cullFaces.push(world < 0 ? 0 : 1 << world);
|
|
107632
|
+
}
|
|
107633
|
+
}
|
|
107634
|
+
geometry = compactQuads(geometry, keep);
|
|
107635
|
+
const template = {
|
|
107636
|
+
geometry,
|
|
107637
|
+
atlas,
|
|
107638
|
+
cullFaces: new Uint8Array(cullFaces),
|
|
107639
|
+
occludes: ModelCulling.isOpaqueFullCube(atlas) && ModelCulling.toLocalMask(63, rotation) === 63,
|
|
107640
|
+
layer: atlas.hasTranslucency ? 1 : 0
|
|
107641
|
+
};
|
|
107642
|
+
this.templates.add(template);
|
|
107643
|
+
return template;
|
|
107644
|
+
});
|
|
107026
107645
|
}
|
|
107027
107646
|
/** Disposes prepared geometry and clears this world's template caches. */
|
|
107028
107647
|
clear() {
|
|
@@ -107358,7 +107977,6 @@ gl_FragDepth=readDepth(vUv);
|
|
|
107358
107977
|
}
|
|
107359
107978
|
try {
|
|
107360
107979
|
await this.clearChunkColumn(chunk.x, chunk.z);
|
|
107361
|
-
let sliceStart = performance.now();
|
|
107362
107980
|
for (const section of chunk.sections) {
|
|
107363
107981
|
if (section.biomes) {
|
|
107364
107982
|
const position = new Vector3(chunk.x * 16, section.y * 16, chunk.z * 16);
|
|
@@ -107372,6 +107990,9 @@ gl_FragDepth=readDepth(vUv);
|
|
|
107372
107990
|
if (!column) this.biomes.set(key, column = /* @__PURE__ */ new Map());
|
|
107373
107991
|
column.set(section.y, copy);
|
|
107374
107992
|
}
|
|
107993
|
+
}
|
|
107994
|
+
let sliceStart = performance.now();
|
|
107995
|
+
for (const section of chunk.sections) {
|
|
107375
107996
|
if (!executor) {
|
|
107376
107997
|
if (!occupiedSections.has(section.y)) continue;
|
|
107377
107998
|
const position = new Vector3(chunk.x * 16, section.y * 16, chunk.z * 16);
|
|
@@ -107536,18 +108157,34 @@ gl_FragDepth=readDepth(vUv);
|
|
|
107536
108157
|
const key = this.worldPosToChunkKey(pos);
|
|
107537
108158
|
let chunk = this._chunks.get(key);
|
|
107538
108159
|
if (typeof chunk === "undefined") {
|
|
108160
|
+
const x4 = Math.floor(pos.x / 16), y5 = Math.floor(pos.y / 16), z4 = Math.floor(pos.z / 16);
|
|
107539
108161
|
chunk = new Chunk(
|
|
107540
108162
|
this.scene,
|
|
107541
|
-
|
|
107542
|
-
|
|
107543
|
-
|
|
108163
|
+
x4,
|
|
108164
|
+
y5,
|
|
108165
|
+
z4,
|
|
107544
108166
|
(positions) => this.updateCulling(positions),
|
|
107545
108167
|
this.sectionModels,
|
|
107546
|
-
(
|
|
107547
|
-
const cx = Math.floor(
|
|
108168
|
+
(x5, y6, z5) => {
|
|
108169
|
+
const cx = Math.floor(x5 / 16), cy = Math.floor(y6 / 16), cz = Math.floor(z5 / 16);
|
|
107548
108170
|
const section = this._chunks.get(`${cx}_${cy}_${cz}`);
|
|
107549
|
-
const index = (
|
|
108171
|
+
const index = (y6 - cy * 16) * 256 + (z5 - cz * 16) * 16 + x5 - cx * 16;
|
|
107550
108172
|
return (section?.fluidByteIndex(index) ?? 0) | (section?.isOccludingIndex(index) ? 64 : 0);
|
|
108173
|
+
},
|
|
108174
|
+
(x5, y6, z5) => this.getBiomeAt(x5, y6, z5),
|
|
108175
|
+
async (biomes) => {
|
|
108176
|
+
if (this._chunks.get(key) !== chunk) return;
|
|
108177
|
+
const columnKey = `${x4}_${z4}`;
|
|
108178
|
+
let column = this.biomes.get(columnKey);
|
|
108179
|
+
if (biomes) {
|
|
108180
|
+
if (!column) this.biomes.set(columnKey, column = /* @__PURE__ */ new Map());
|
|
108181
|
+
column.set(y5, biomes);
|
|
108182
|
+
} else {
|
|
108183
|
+
column?.delete(y5);
|
|
108184
|
+
if (!column?.size) this.biomes.delete(columnKey);
|
|
108185
|
+
}
|
|
108186
|
+
await chunk.refreshBiomes();
|
|
108187
|
+
await this._chunks.get(`${x4}_${y5 + 1}_${z4}`)?.refreshBiomes();
|
|
107551
108188
|
}
|
|
107552
108189
|
);
|
|
107553
108190
|
this._chunks.set(key, chunk);
|
|
@@ -107608,6 +108245,7 @@ gl_FragDepth=readDepth(vUv);
|
|
|
107608
108245
|
if (!Number.isInteger(maxAtlasSize) || maxAtlasSize < 1) throw new RangeError("Section atlas size must be a positive integer");
|
|
107609
108246
|
if (count > indices.length || count > templates.length || count > cullMasks.length) throw new RangeError("Section entry count exceeds its arrays");
|
|
107610
108247
|
if (fluids && fluids.cells.length !== 5832) throw new RangeError("Section fluid cells must cover an 18\xD718\xD718 neighborhood");
|
|
108248
|
+
if (fluids?.waterTints && fluids.waterTints.length !== 4096 * 3) throw new RangeError("Section water tints must contain RGB for 4096 cells");
|
|
107611
108249
|
for (const template of templateData) {
|
|
107612
108250
|
const { quads } = template;
|
|
107613
108251
|
if (template.positions.length !== quads * 12 || template.normals.length !== quads * 12 || template.uvs.length !== quads * 8 || template.uvBounds.length !== quads * 16 || template.colors.length !== quads * 12 || template.indices.length !== quads * 6 || template.cullFaces.length !== quads) {
|
|
@@ -107685,7 +108323,9 @@ gl_FragDepth=readDepth(vUv);
|
|
|
107685
108323
|
height
|
|
107686
108324
|
});
|
|
107687
108325
|
}
|
|
107688
|
-
|
|
108326
|
+
const tintIndex = (x4 + z4 * 16 + y5 * 256) * 3;
|
|
108327
|
+
const tint = fluid === "water" && fluids.waterTints ? fluids.waterTints.subarray(tintIndex, tintIndex + 3) : data.tint;
|
|
108328
|
+
fluidPages.get(fluid).fluids.push({ quads, x: x4, y: y5, z: z4, data, tint });
|
|
107689
108329
|
}
|
|
107690
108330
|
pages.push(...[...fluidPages.values()].sort((a4, b4) => Number(atlases[a4.placements[0].atlas].animated) - Number(atlases[b4.placements[0].atlas].animated) || a4.placements[0].atlas - b4.placements[0].atlas));
|
|
107691
108331
|
}
|
|
@@ -107734,7 +108374,7 @@ gl_FragDepth=readDepth(vUv);
|
|
|
107734
108374
|
for (let corner = 0; corner < 6; corner++) outputIndices[indexOffset++] = start + template.indices[quad * 6 + corner];
|
|
107735
108375
|
}
|
|
107736
108376
|
}
|
|
107737
|
-
for (const { quads, x: x4, y: y5, z: z4, data } of page.fluids) {
|
|
108377
|
+
for (const { quads, x: x4, y: y5, z: z4, data, tint } of page.fluids) {
|
|
107738
108378
|
const atlas = atlases[data.atlas];
|
|
107739
108379
|
const placement = page.placements[0];
|
|
107740
108380
|
const mapU = (u4) => (placement.x + u4 * atlas.width) / page.width;
|
|
@@ -107758,7 +108398,7 @@ gl_FragDepth=readDepth(vUv);
|
|
|
107758
108398
|
mapU((rect[0] + rect[2]) / atlas.width),
|
|
107759
108399
|
mapV(1 - rect[1] / atlas.height)
|
|
107760
108400
|
], vertex2 * 4);
|
|
107761
|
-
colors.set(
|
|
108401
|
+
colors.set(tint, vertex2 * 3);
|
|
107762
108402
|
}
|
|
107763
108403
|
outputIndices.set([start, start + 1, start + 2, start, start + 2, start + 3], indexOffset);
|
|
107764
108404
|
indexOffset += 6;
|
|
@@ -107902,7 +108542,7 @@ gl_FragDepth=readDepth(vUv);
|
|
|
107902
108542
|
input.cullMasks[i4] = cullMask;
|
|
107903
108543
|
}
|
|
107904
108544
|
if (fluids) {
|
|
107905
|
-
input.fluids = { cells: fluids.cells };
|
|
108545
|
+
input.fluids = { cells: fluids.cells, waterTints: fluids.waterTints };
|
|
107906
108546
|
for (const kind of ["water", "lava"]) {
|
|
107907
108547
|
const atlas = fluids[kind];
|
|
107908
108548
|
if (!atlas) continue;
|
|
@@ -108003,11 +108643,14 @@ gl_FragDepth=readDepth(vUv);
|
|
|
108003
108643
|
init_FluidGeometry();
|
|
108004
108644
|
init_FluidQuads();
|
|
108005
108645
|
init_CubeFace();
|
|
108646
|
+
var WATER_TINT2 = new Color(4159204).toArray();
|
|
108006
108647
|
var Chunk = class _Chunk {
|
|
108007
|
-
constructor(scene, x4, y5, z4, onBlocksChanged, sectionModels, neighborCell) {
|
|
108648
|
+
constructor(scene, x4, y5, z4, onBlocksChanged, sectionModels, neighborCell, biomeAt, onBiomesChanged) {
|
|
108008
108649
|
this.onBlocksChanged = onBlocksChanged;
|
|
108009
108650
|
this.sectionModels = sectionModels;
|
|
108010
108651
|
this.neighborCell = neighborCell;
|
|
108652
|
+
this.biomeAt = biomeAt;
|
|
108653
|
+
this.onBiomesChanged = onBiomesChanged;
|
|
108011
108654
|
this.data = new ChunkData();
|
|
108012
108655
|
this.renderedBlocks = /* @__PURE__ */ new Map();
|
|
108013
108656
|
this.sectionBlocks = /* @__PURE__ */ new Map();
|
|
@@ -108032,6 +108675,56 @@ gl_FragDepth=readDepth(vUv);
|
|
|
108032
108675
|
const index = _Chunk.chunkPosToBlockIndex(pos);
|
|
108033
108676
|
return this.renderedBlocks.get(index);
|
|
108034
108677
|
}
|
|
108678
|
+
getBiomeAt(posOrX, y5, z4) {
|
|
108679
|
+
if (typeof posOrX === "number") return this.getBiomeAt(new Vector3(posOrX, y5, z4));
|
|
108680
|
+
if (isTripleArray(posOrX)) return this.getBiomeAt(new Vector3(...posOrX));
|
|
108681
|
+
const pos = this.worldPosToChunkPos(posOrX);
|
|
108682
|
+
_Chunk.chunkPosToBlockIndex(pos);
|
|
108683
|
+
return this.biomeAt ? this.biomeAt(posOrX.x, posOrX.y, posOrX.z) : this.biomes?.[Math.floor(pos.x / 4) + Math.floor(pos.z / 4) * 4 + Math.floor(pos.y / 4) * 16];
|
|
108684
|
+
}
|
|
108685
|
+
/** Copies 64 biome IDs in x + z * 4 + y * 16 order and refreshes placed blocks. Omit the array to clear biome data. */
|
|
108686
|
+
setBiomes(biomes) {
|
|
108687
|
+
const copy = biomes ? [...biomes] : void 0;
|
|
108688
|
+
if (copy && (copy.length !== 64 || !copy.every((id) => typeof id === "string" && id.length > 0))) {
|
|
108689
|
+
throw new RangeError("Section biomes must contain 64 nonempty biome IDs");
|
|
108690
|
+
}
|
|
108691
|
+
if (this.onBiomesChanged) return this.onBiomesChanged(copy);
|
|
108692
|
+
this.biomes = copy;
|
|
108693
|
+
return this.refreshBiomes();
|
|
108694
|
+
}
|
|
108695
|
+
/** Rebuilds biome-tinted blocks while preserving hidden blocks and unrelated render objects. */
|
|
108696
|
+
async refreshBiomes() {
|
|
108697
|
+
const affected = /* @__PURE__ */ new Map();
|
|
108698
|
+
const blocks = [];
|
|
108699
|
+
for (const index of this.renderedBlocks.keys()) {
|
|
108700
|
+
const block = this.data.get(index);
|
|
108701
|
+
const stateKey = ChunkData.paletteKey(block);
|
|
108702
|
+
let matches = affected.get(stateKey);
|
|
108703
|
+
if (!matches) {
|
|
108704
|
+
const key = AssetKey.parse("blockstates", block.type);
|
|
108705
|
+
matches = BlockStates.get(key).then(async (state) => {
|
|
108706
|
+
const origin = state?.key ?? key;
|
|
108707
|
+
const [source, fluid] = await Promise.all([BlockTints.biomeSource(origin), getBlockFluidState(origin, block.properties)]);
|
|
108708
|
+
return !!source || fluid?.kind === "water";
|
|
108709
|
+
});
|
|
108710
|
+
affected.set(stateKey, matches);
|
|
108711
|
+
}
|
|
108712
|
+
if (await matches) blocks.push({ index, block });
|
|
108713
|
+
}
|
|
108714
|
+
if (!blocks.length) return;
|
|
108715
|
+
const hidden = new Set(this.hiddenBlocks);
|
|
108716
|
+
try {
|
|
108717
|
+
await this.placeBlocks(blocks);
|
|
108718
|
+
} finally {
|
|
108719
|
+
for (const index of hidden) {
|
|
108720
|
+
this.hiddenBlocks.add(index);
|
|
108721
|
+
this.renderedBlocks.get(index)?.object?.setVisible(false);
|
|
108722
|
+
}
|
|
108723
|
+
const positions = blocks.map(({ index }) => new Vector3(...this.positionAt(index)));
|
|
108724
|
+
if (this.onBlocksChanged) await this.onBlocksChanged(positions);
|
|
108725
|
+
else await this.rebuildSectionMesh();
|
|
108726
|
+
}
|
|
108727
|
+
}
|
|
108035
108728
|
async setBlockAt(posOrX, yOrBlock, z4, block) {
|
|
108036
108729
|
if (typeof posOrX == "number") {
|
|
108037
108730
|
return this.setBlockAt(new Vector3(posOrX, yOrBlock, z4), block);
|
|
@@ -108070,14 +108763,15 @@ gl_FragDepth=readDepth(vUv);
|
|
|
108070
108763
|
nbt: block.nbt === void 0 ? void 0 : structuredClone(block.nbt)
|
|
108071
108764
|
} : void 0
|
|
108072
108765
|
}));
|
|
108073
|
-
const states =
|
|
108074
|
-
const
|
|
108075
|
-
|
|
108076
|
-
|
|
108077
|
-
|
|
108078
|
-
|
|
108079
|
-
|
|
108080
|
-
|
|
108766
|
+
const states = /* @__PURE__ */ new Map();
|
|
108767
|
+
for (const { index, key, block } of placements) {
|
|
108768
|
+
if (key === void 0) continue;
|
|
108769
|
+
let state = states.get(key);
|
|
108770
|
+
if (!state) states.set(key, state = { stored: block, indices: [] });
|
|
108771
|
+
state.indices.push(index);
|
|
108772
|
+
}
|
|
108773
|
+
const biomes = /* @__PURE__ */ new Map();
|
|
108774
|
+
const settled = await Promise.allSettled([...states.values()].map(({ stored, indices }) => this.resolveState(stored, indices, biomes)));
|
|
108081
108775
|
const resolutions = new Map([...states.keys()].map((key, i4) => [key, settled[i4]]));
|
|
108082
108776
|
const positions = [];
|
|
108083
108777
|
let failed = false, failure;
|
|
@@ -108101,7 +108795,8 @@ gl_FragDepth=readDepth(vUv);
|
|
|
108101
108795
|
if (!readBlock) continue;
|
|
108102
108796
|
const resolved = resolutions.get(key);
|
|
108103
108797
|
if (resolved.status === "rejected") throw resolved.reason;
|
|
108104
|
-
const { blockState: blockState3, perBlock, fluid, prepared, stored } = resolved.value;
|
|
108798
|
+
const { blockState: blockState3, perBlock, fluid, prepared, contexts, stored } = resolved.value;
|
|
108799
|
+
const context = contexts.get(index);
|
|
108105
108800
|
if (!blockState3) {
|
|
108106
108801
|
this.data.assign(index, 0);
|
|
108107
108802
|
continue;
|
|
@@ -108109,9 +108804,10 @@ gl_FragDepth=readDepth(vUv);
|
|
|
108109
108804
|
const variantPosition = worldPos.toArray();
|
|
108110
108805
|
if (fluid) {
|
|
108111
108806
|
this.fluidCells[index] = (fluid.kind === "water" ? 16 : 32) | Math.min(fluid.level, 8);
|
|
108807
|
+
if (fluid.kind === "water") this.setWaterTint(index, context?.waterTint);
|
|
108112
108808
|
this.meshDirty = true;
|
|
108113
108809
|
}
|
|
108114
|
-
const templates = perBlock ? void 0 : fluid?.renderModel === false ? [] : prepared?.pick(variantPosition);
|
|
108810
|
+
const templates = perBlock ? void 0 : fluid?.renderModel === false ? [] : (context?.prepared ?? prepared)?.pick(variantPosition);
|
|
108115
108811
|
if (templates) {
|
|
108116
108812
|
this.sectionBlocks.set(index, templates.map((template) => ({ index, template, cullMask: 0 })));
|
|
108117
108813
|
this.meshDirty = true;
|
|
@@ -108121,7 +108817,9 @@ gl_FragDepth=readDepth(vUv);
|
|
|
108121
108817
|
instanceMeshes: true,
|
|
108122
108818
|
maxInstanceCount: 2e3,
|
|
108123
108819
|
initialState: stored.properties,
|
|
108124
|
-
variantPosition
|
|
108820
|
+
variantPosition,
|
|
108821
|
+
biome: context?.biome,
|
|
108822
|
+
biomePosition: this.biomePosition(index, blockState3, stored)
|
|
108125
108823
|
});
|
|
108126
108824
|
object4.setPosition(MineRenderWorld.worldToScenePosition(worldPos));
|
|
108127
108825
|
}
|
|
@@ -108144,24 +108842,21 @@ gl_FragDepth=readDepth(vUv);
|
|
|
108144
108842
|
for (const info of this.renderedBlocks.values()) info.object?.removeFromScene();
|
|
108145
108843
|
this.sectionBlocks.clear();
|
|
108146
108844
|
this.fluidCells.fill(0);
|
|
108845
|
+
this.waterTints = void 0;
|
|
108147
108846
|
this.renderedBlocks.clear();
|
|
108148
108847
|
this.hiddenBlocks.clear();
|
|
108149
108848
|
this.meshDirty = true;
|
|
108150
108849
|
this.data.copyFrom(data);
|
|
108151
|
-
const ids = /* @__PURE__ */ new
|
|
108850
|
+
const ids = /* @__PURE__ */ new Map();
|
|
108152
108851
|
for (let index = 0; index < 4096; index++) {
|
|
108153
108852
|
const id = this.data.idAt(index);
|
|
108154
|
-
if (id)
|
|
108155
|
-
|
|
108156
|
-
|
|
108157
|
-
|
|
108158
|
-
|
|
108159
|
-
|
|
108160
|
-
|
|
108161
|
-
const fluid = await getBlockFluidState(blockState3?.key, state.properties);
|
|
108162
|
-
const prepared = perBlock || fluid?.renderModel === false ? void 0 : await this.sectionModels.prepareState(blockState3, state.properties);
|
|
108163
|
-
return { blockState: blockState3, perBlock, fluid, prepared };
|
|
108164
|
-
}));
|
|
108853
|
+
if (!id) continue;
|
|
108854
|
+
let indices = ids.get(id);
|
|
108855
|
+
if (!indices) ids.set(id, indices = []);
|
|
108856
|
+
indices.push(index);
|
|
108857
|
+
}
|
|
108858
|
+
const palette = [...ids.keys()], biomes = /* @__PURE__ */ new Map();
|
|
108859
|
+
const settled = await Promise.allSettled(palette.map((id) => this.resolveState(this.data.stateAt(id), ids.get(id), biomes)));
|
|
108165
108860
|
const resolutions = new Map(palette.map((id, i4) => [id, settled[i4]]));
|
|
108166
108861
|
const perBlocks = [];
|
|
108167
108862
|
let failed = false, failure;
|
|
@@ -108171,24 +108866,28 @@ gl_FragDepth=readDepth(vUv);
|
|
|
108171
108866
|
try {
|
|
108172
108867
|
const resolved = resolutions.get(id);
|
|
108173
108868
|
if (resolved.status === "rejected") throw resolved.reason;
|
|
108174
|
-
const { blockState: blockState3, perBlock, fluid, prepared } = resolved.value;
|
|
108869
|
+
const { blockState: blockState3, perBlock, fluid, prepared, contexts } = resolved.value;
|
|
108870
|
+
const context = contexts.get(index);
|
|
108175
108871
|
if (!blockState3) {
|
|
108176
108872
|
this.data.assign(index, 0);
|
|
108177
108873
|
this.fluidCells[index] = 0;
|
|
108178
108874
|
continue;
|
|
108179
108875
|
}
|
|
108180
|
-
if (fluid)
|
|
108876
|
+
if (fluid) {
|
|
108877
|
+
this.fluidCells[index] = (fluid.kind === "water" ? 16 : 32) | Math.min(fluid.level, 8);
|
|
108878
|
+
if (fluid.kind === "water") this.setWaterTint(index, context?.waterTint);
|
|
108879
|
+
}
|
|
108181
108880
|
const variantPosition = [
|
|
108182
108881
|
this.x * 16 + index % 16,
|
|
108183
108882
|
this.y * 16 + Math.floor(index / 256),
|
|
108184
108883
|
this.z * 16 + Math.floor(index / 16) % 16
|
|
108185
108884
|
];
|
|
108186
|
-
const templates = perBlock ? void 0 : fluid?.renderModel === false ? [] : prepared?.pick(variantPosition);
|
|
108885
|
+
const templates = perBlock ? void 0 : fluid?.renderModel === false ? [] : (context?.prepared ?? prepared)?.pick(variantPosition);
|
|
108187
108886
|
if (templates) {
|
|
108188
108887
|
this.sectionBlocks.set(index, templates.map((template) => ({ index, template, cullMask: 0 })));
|
|
108189
108888
|
this.meshDirty = true;
|
|
108190
108889
|
} else {
|
|
108191
|
-
perBlocks.push({ index, blockState: blockState3 });
|
|
108890
|
+
perBlocks.push({ index, blockState: blockState3, biome: context?.biome });
|
|
108192
108891
|
}
|
|
108193
108892
|
const readBlock = this.data.snapshot(index);
|
|
108194
108893
|
this.renderedBlocks.set(index, { get block() {
|
|
@@ -108201,7 +108900,7 @@ gl_FragDepth=readDepth(vUv);
|
|
|
108201
108900
|
failed = true;
|
|
108202
108901
|
}
|
|
108203
108902
|
}
|
|
108204
|
-
for (const { index, blockState: blockState3 } of perBlocks) {
|
|
108903
|
+
for (const { index, blockState: blockState3, biome } of perBlocks) {
|
|
108205
108904
|
let object4;
|
|
108206
108905
|
try {
|
|
108207
108906
|
object4 = await this.scene.addBlock(blockState3, {
|
|
@@ -108209,11 +108908,9 @@ gl_FragDepth=readDepth(vUv);
|
|
|
108209
108908
|
instanceMeshes: true,
|
|
108210
108909
|
maxInstanceCount: 2e3,
|
|
108211
108910
|
initialState: this.data.stateAt(this.data.idAt(index)).properties,
|
|
108212
|
-
variantPosition:
|
|
108213
|
-
|
|
108214
|
-
|
|
108215
|
-
this.z * 16 + Math.floor(index / 16) % 16
|
|
108216
|
-
]
|
|
108911
|
+
variantPosition: this.positionAt(index),
|
|
108912
|
+
biome,
|
|
108913
|
+
biomePosition: this.biomePosition(index, blockState3, this.data.stateAt(this.data.idAt(index)))
|
|
108217
108914
|
});
|
|
108218
108915
|
object4.setPosition(new Vector3(
|
|
108219
108916
|
this.x * 256 + index % 16 * 16,
|
|
@@ -108232,6 +108929,68 @@ gl_FragDepth=readDepth(vUv);
|
|
|
108232
108929
|
}
|
|
108233
108930
|
if (failed) throw failure;
|
|
108234
108931
|
}
|
|
108932
|
+
positionAt(index) {
|
|
108933
|
+
return [this.x * 16 + index % 16, this.y * 16 + Math.floor(index / 256), this.z * 16 + Math.floor(index / 16) % 16];
|
|
108934
|
+
}
|
|
108935
|
+
biomePosition(index, blockState3, stored) {
|
|
108936
|
+
const position = this.positionAt(index), name2 = blockState3.key?.toNamespacedString();
|
|
108937
|
+
if (stored.properties?.half === "upper" && (name2 === "minecraft:tall_grass" || name2 === "minecraft:large_fern")) position[1]--;
|
|
108938
|
+
return position;
|
|
108939
|
+
}
|
|
108940
|
+
async resolveState(stored, indices, biomes) {
|
|
108941
|
+
const blockState3 = await BlockStates.get(AssetKey.parse("blockstates", stored.type));
|
|
108942
|
+
const perBlock = !blockState3 || !this.sectionModels || !!(blockState3.key && BlockEntities.entry(await BlockEntities.getIndex(blockState3.key.root), blockState3.key.toNamespacedString()));
|
|
108943
|
+
const fluid = await getBlockFluidState(blockState3?.key, stored.properties);
|
|
108944
|
+
const hasBiomes = this.getBiomeAt(this.x * 16, this.y * 16, this.z * 16) !== void 0 || this.biomeAt?.(this.x * 16, this.y * 16 - 1, this.z * 16) !== void 0;
|
|
108945
|
+
const source = hasBiomes && blockState3 ? await BlockTints.biomeSource(blockState3.key) : void 0;
|
|
108946
|
+
const prepare = (color3) => perBlock || fluid?.renderModel === false ? void 0 : this.sectionModels.prepareState(blockState3, stored.properties, color3);
|
|
108947
|
+
const contexts = /* @__PURE__ */ new Map();
|
|
108948
|
+
const groups = /* @__PURE__ */ new Map();
|
|
108949
|
+
if (blockState3 && (source || fluid?.kind === "water")) {
|
|
108950
|
+
for (const index of indices) {
|
|
108951
|
+
const position = this.biomePosition(index, blockState3, stored);
|
|
108952
|
+
const biome = this.biomeAt ? this.biomeAt(...position) : position[1] >= this.y * 16 ? this.getBiomeAt(position) : void 0;
|
|
108953
|
+
if (!biome) continue;
|
|
108954
|
+
const key = JSON.stringify(source === "grass" ? [biome, position[0], position[2]] : [biome]);
|
|
108955
|
+
let group = groups.get(key);
|
|
108956
|
+
if (!group) groups.set(key, group = { biome, position, indices: [] });
|
|
108957
|
+
group.indices.push(index);
|
|
108958
|
+
}
|
|
108959
|
+
}
|
|
108960
|
+
const groupedCount = [...groups.values()].reduce((sum, group) => sum + group.indices.length, 0);
|
|
108961
|
+
const prepared = groupedCount < indices.length ? await prepare() : void 0;
|
|
108962
|
+
await Promise.all([...groups.values()].map(async ({ biome, position, indices: indices2 }) => {
|
|
108963
|
+
const available = () => {
|
|
108964
|
+
const key = JSON.stringify([biome, blockState3?.key?.root]);
|
|
108965
|
+
let found = biomes.get(key);
|
|
108966
|
+
if (!found) {
|
|
108967
|
+
found = Biomes.get(biome, blockState3?.key).then((value) => value !== void 0);
|
|
108968
|
+
biomes.set(key, found);
|
|
108969
|
+
}
|
|
108970
|
+
return found;
|
|
108971
|
+
};
|
|
108972
|
+
const context = { biome };
|
|
108973
|
+
if (perBlock) {
|
|
108974
|
+
if (!await available()) context.biome = void 0;
|
|
108975
|
+
} else {
|
|
108976
|
+
context.prepared = await prepare(async () => await available() ? BlockTints.getBiomeColor(blockState3?.key, biome, position) : void 0);
|
|
108977
|
+
if (fluid?.kind === "water" && await available()) {
|
|
108978
|
+
const color3 = await Biomes.getColor(biome, "water", blockState3?.key);
|
|
108979
|
+
if (color3 !== void 0 && color3 !== 4159204) context.waterTint = new Color(color3).toArray();
|
|
108980
|
+
}
|
|
108981
|
+
}
|
|
108982
|
+
for (const index of indices2) contexts.set(index, context);
|
|
108983
|
+
}));
|
|
108984
|
+
return { blockState: blockState3, perBlock, fluid, prepared, contexts, stored };
|
|
108985
|
+
}
|
|
108986
|
+
setWaterTint(index, tint) {
|
|
108987
|
+
if (!this.sectionModels || !this.waterTints && tint === void 0) return;
|
|
108988
|
+
if (!this.waterTints) {
|
|
108989
|
+
this.waterTints = new Float32Array(4096 * 3);
|
|
108990
|
+
for (let cell = 0; cell < 4096; cell++) this.waterTints.set(WATER_TINT2, cell * 3);
|
|
108991
|
+
}
|
|
108992
|
+
this.waterTints.set(tint ?? WATER_TINT2, index * 3);
|
|
108993
|
+
}
|
|
108235
108994
|
/** Changes visibility at world block coordinates while preserving the block's data. */
|
|
108236
108995
|
async setBlockVisibleAt(pos, visible) {
|
|
108237
108996
|
const index = _Chunk.chunkPosToBlockIndex(this.worldPosToChunkPos(pos));
|
|
@@ -108335,7 +109094,7 @@ gl_FragDepth=readDepth(vUv);
|
|
|
108335
109094
|
if (block && !block.object) origins.set(kind, block.block.type);
|
|
108336
109095
|
}
|
|
108337
109096
|
if (origins.size) {
|
|
108338
|
-
fluids = { cells: new Uint8Array(18 * 18 * 18) };
|
|
109097
|
+
fluids = { cells: new Uint8Array(18 * 18 * 18), waterTints: this.waterTints?.slice() };
|
|
108339
109098
|
for (let y5 = -1; y5 <= 16; y5++) {
|
|
108340
109099
|
for (let z4 = -1; z4 <= 16; z4++) {
|
|
108341
109100
|
for (let x4 = -1; x4 <= 16; x4++) {
|
|
@@ -108377,8 +109136,13 @@ gl_FragDepth=readDepth(vUv);
|
|
|
108377
109136
|
this.renderedBlocks.clear();
|
|
108378
109137
|
this.hiddenBlocks.clear();
|
|
108379
109138
|
this.fluidCells.fill(0);
|
|
109139
|
+
this.waterTints = void 0;
|
|
108380
109140
|
this.data.clear();
|
|
108381
|
-
|
|
109141
|
+
this.biomes = void 0;
|
|
109142
|
+
if (notify) {
|
|
109143
|
+
await this.onBiomesChanged?.(void 0);
|
|
109144
|
+
await this.onBlocksChanged?.(positions);
|
|
109145
|
+
}
|
|
108382
109146
|
}
|
|
108383
109147
|
async dispose() {
|
|
108384
109148
|
await this.clear();
|