minerender 2.1.0-alpha.94 → 2.1.0-alpha.95

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/bundle.js CHANGED
@@ -111389,7 +111389,7 @@ property list uchar int vertex_index
111389
111389
  return typeof value === "string" && state[key] !== void 0 && value.split("|").includes(`${state[key]}`);
111390
111390
  });
111391
111391
  }
111392
- var BlockStateResolver = class {
111392
+ var BlockStateResolver = class _BlockStateResolver {
111393
111393
  /** Loads vanilla property defaults, falling back to preview values inferred from the blockstate file. */
111394
111394
  static async defaults(blockState3) {
111395
111395
  const defaults = blockState3.key ? await BlockStates.getDefaultState(blockState3.key) : void 0;
@@ -111412,7 +111412,7 @@ property list uchar int vertex_index
111412
111412
  }
111413
111413
  /** Selects matching models. Supply `choose` to control selection within each alternatives array. */
111414
111414
  static select(blockState3, state, choose = this.choose) {
111415
- return this.matching(blockState3, state).map(choose);
111415
+ return this.matching(blockState3, state).map((variants) => choose(variants));
111416
111416
  }
111417
111417
  /** Returns matching model groups before choosing weighted alternatives. */
111418
111418
  static matching(blockState3, state) {
@@ -111438,8 +111438,8 @@ property list uchar int vertex_index
111438
111438
  }
111439
111439
  return out;
111440
111440
  }
111441
- /** Selects a random alternative using positive integer weights, each defaulting to 1. */
111442
- static choose(variants) {
111441
+ /** Selects by positive integer weights (default 1); world block coordinates make the choice repeatable. */
111442
+ static choose(variants, position) {
111443
111443
  if (!Array.isArray(variants)) return variants;
111444
111444
  if (!variants.length) throw new MineRenderError("Blockstate variant arrays must not be empty");
111445
111445
  const total = variants.reduce((sum, variant) => {
@@ -111449,13 +111449,29 @@ property list uchar int vertex_index
111449
111449
  }
111450
111450
  return sum + weight;
111451
111451
  }, 0);
111452
- let choice = Math.random() * total;
111452
+ let choice = position === void 0 ? Math.random() * total : _BlockStateResolver.positionSample(position, total);
111453
111453
  for (const variant of variants) {
111454
111454
  choice -= variant.weight ?? 1;
111455
111455
  if (choice < 0) return variant;
111456
111456
  }
111457
111457
  return variants[variants.length - 1];
111458
111458
  }
111459
+ static positionSample(position, bound) {
111460
+ if (bound > 2147483647) {
111461
+ throw new MineRenderError("Position-based blockstate variant total weight must not exceed 2147483647");
111462
+ }
111463
+ let mixed = BigInt(Math.imul(position[0], 3129871)) ^ BigInt(position[2]) * 116129781n ^ BigInt(position[1]);
111464
+ mixed = BigInt.asIntN(64, mixed * mixed * 42317861n + mixed * 11n) >> 16n;
111465
+ let seed = (mixed ^ 0x5deece66dn) & 0xffffffffffffn;
111466
+ let bits2, value;
111467
+ do {
111468
+ seed = seed * 0x5deece66dn + 11n & 0xffffffffffffn;
111469
+ bits2 = Number(seed >> 17n);
111470
+ if ((bound & bound - 1) === 0) return Number(BigInt(bound) * BigInt(bits2) >> 31n);
111471
+ value = bits2 % bound;
111472
+ } while ((bits2 - value + bound - 1 | 0) < 0);
111473
+ return value;
111474
+ }
111459
111475
  /** Converts blockstate rotations in degrees into the Euler rotation used by model rendering. */
111460
111476
  static rotation(variant) {
111461
111477
  const rotation = new Euler();
@@ -111586,6 +111602,7 @@ property list uchar int vertex_index
111586
111602
  this._entityPlacement = new Matrix4();
111587
111603
  this._entityGeneration = 0;
111588
111604
  this.options = (0, import_ts_deepmerge6.default)({}, _BlockObject.DEFAULT_OPTIONS, options ?? {});
111605
+ this.variantPosition = options?.variantPosition ? [...options.variantPosition] : void 0;
111589
111606
  }
111590
111607
  async init() {
111591
111608
  if (this.options.applyDefaultState) {
@@ -111822,7 +111839,7 @@ property list uchar int vertex_index
111822
111839
  return !!(await Models.getMerged(modelKey))?.elements?.length;
111823
111840
  }
111824
111841
  getSingleVariant(variants) {
111825
- return BlockStateResolver.choose(variants);
111842
+ return BlockStateResolver.choose(variants, this.variantPosition);
111826
111843
  }
111827
111844
  // @deprecated
111828
111845
  async createAVariant(variants, instanceInfo) {
@@ -119828,13 +119845,14 @@ gl_FragDepth=readDepth(vUv);
119828
119845
  if (!Number.isInteger(maxAtlasSize) || maxAtlasSize < 1) throw new RangeError("maxAtlasSize must be a positive integer");
119829
119846
  }
119830
119847
  /** Returns templates for the matched parts, or `undefined` when the block needs an individual render object. */
119831
- async get(blockState3, properties = {}) {
119848
+ async get(blockState3, properties = {}, position) {
119849
+ const variantPosition = position ? [...position] : void 0;
119832
119850
  let states = this.states.get(blockState3);
119833
119851
  if (!states) this.states.set(blockState3, states = /* @__PURE__ */ new Map());
119834
119852
  const key = JSON.stringify(Object.entries(properties).sort(([a4], [b4]) => a4.localeCompare(b4)));
119835
119853
  const prepared = await cached(states, key, () => this.prepare(blockState3, properties));
119836
119854
  if (!prepared) return void 0;
119837
- return prepared.groups.map((group) => prepared.templates.get(BlockStateResolver.choose(group)));
119855
+ return prepared.groups.map((group) => prepared.templates.get(BlockStateResolver.choose(group, variantPosition)));
119838
119856
  }
119839
119857
  async prepare(blockState3, properties) {
119840
119858
  const state = { ...await BlockStateResolver.defaults(blockState3), ...properties };
@@ -120632,7 +120650,8 @@ gl_FragDepth=readDepth(vUv);
120632
120650
  this.data.set(index, void 0);
120633
120651
  continue;
120634
120652
  }
120635
- const templates = perBlock ? void 0 : await this.sectionModels.get(blockState3, stored.properties);
120653
+ const variantPosition = worldPos.toArray();
120654
+ const templates = perBlock ? void 0 : await this.sectionModels.get(blockState3, stored.properties, variantPosition);
120636
120655
  if (templates) {
120637
120656
  this.sectionBlocks.set(index, templates.map((template) => ({ index, template, cullMask: 0 })));
120638
120657
  this.meshDirty = true;
@@ -120641,7 +120660,8 @@ gl_FragDepth=readDepth(vUv);
120641
120660
  mergeMeshes: true,
120642
120661
  instanceMeshes: true,
120643
120662
  maxInstanceCount: 2e3,
120644
- initialState: stored.properties
120663
+ initialState: stored.properties,
120664
+ variantPosition
120645
120665
  });
120646
120666
  object3.setPosition(MineRenderWorld.worldToScenePosition(worldPos));
120647
120667
  }