FOUNDATION 06 · RESOURCE OWNERSHIP

A material counts only after every handoff accepts it

NiceChunk cotton begins as a deterministic PDA rule bound to an eligible grass face, not as a free-standing inventory voxel. Mining stores the supporting terrain block first and adds cotton only when a compatible cotton stack has headroom or a new Backpack record can be opened. Recipe 1025 then requires four cotton units and one dry-grass unit, requires a separate fuel index, consumes exact stack quantities, and creates one volume-bearing cotton-cloth material for the forge.

11 min read
The canonical villager girl mines the grass support beneath cotton beside an open compartmented inventory chest while the villager boy presses four white cotton tufts and one dry-grass bundle into cloth; a separate fuel fire burns nearby and a completed cloth panel moves in the sea breeze.

Key points

Deterministic does not mean already owned

The same seed, coordinate, ordered PDA rows, and rule revision resolve the same cotton candidate. Ownership begins only if the successful mining transaction actually appends the cotton reward to the player's backpack.

The visible reward is deliberately lossy

The mined grass record is strict, but cotton and an exploration extra are secondary records. Cotton is attempted first; either secondary reward is silently skipped when it has neither compatible stack headroom nor a free record. A skipped cotton candidate does not prevent a later exploration candidate from using its own compatible stack.

Smelting consumes stack quantities; forging consumes whole selected slots

The recipe program verifies identities, unique indexes, required quantities, heat, and output capacity, then partially or fully consumes input stacks, consumes one fuel unit, and appends bounded cloth output inside one atomic transaction. The forge later verifies aggregate material capacity and still consumes complete selected records.

SURFACE DECORATION TABLE

Cotton begins as one ordered rule bound to a grass top face

The current SurfaceDecorationTable revision contains forty-three generic numeric rows. Rule 74 maps canonical grass block 1 to cotton drop block 48, uses decoration model 12, occupies roll interval 425 through 454 for salt 201, and carries the shadow and mineable flags. Chunk.js fetches those rows for rendering; the Chunk Program reads the PDA again when it evaluates a reward.

A coordinate must first resolve an uncovered canonical grass surface inside the rule's height range. Water above the surface suppresses the decoration, and a generated tree voxel in the bound space wins instead. Rows using the same salt share one hash roll and are evaluated in stored order, so cotton and the five flower colors occupy disjoint bands rather than running six unrelated random trials.

Current cotton row Rule 74 · decoration 12

Grass block 1 resolves cotton block 48 when the shared roll lies in [425,455).

Conditional roll share 30 / 10,000

A stable 0.3% interval among eligible grass coordinates, not a repeated swing chance.

Rule source SurfaceDecorationTable PDA

The bundled JavaScript defaults are initialization and test fixtures, not the production authority.

ONE ATOMIC MINING ACTION

The program rechecks the support, records the break, and stores grass before cotton

A mining transaction supplies integer coordinates and the client's expected base block. The Chunk Program verifies the session and canonical accounts, rejects a foundation-protected coordinate, regenerates the base block, reads both rule PDAs, and rejects air, water, bedrock, or an expected-block mismatch. A decoration becomes eligible for the secondary reward only when its surface Y and surface block match the block being mined; a mismatch removes that extra without invalidating the base mining action.

The transaction records the broken local coordinate and then invokes the Backpack Program for the required terrain reward. Only after that strict append succeeds does it build a secondary list. Cotton is first, with block ID 48, the supporting coordinate, the same precision-gathering volume, and metadata packing rule ID 74 with decoration ID 12. An optional ResourceDropTable exploration reward follows it.

  1. Reconstruct

    Resolve the canonical block and PDA-driven decoration for the submitted coordinate.

  2. Stage the mandatory state

    Insert the broken coordinate and strictly append the mined support block to the owner's backpack.

  3. Offer ordered extras

    Try cotton first and an exploration drop second without making either one a reason to fail the base mining action.

BACKPACK CAPACITY

Cotton needs compatible stack headroom or a record of its own

The backpack account physically reserves ninety-nine 80-byte records, but current initialization limits a new backpack's active capacity to at most fifty. Item count is dense: records occupy indexes zero through itemCount minus one. The strict grass append happens before the lossy batch, but it increases itemCount only when no compatible grass stack has room and a new record must be opened.

A Backpack with no free records can still retain cotton when a block-48 stack with the same category, flags, and packed rule-74/decoration-12 metadata remains below quantity ninety-nine. Conversely, headroom in an unrelated cotton identity does not help. If grass and cotton both need new records, they consume free records in that order; if grass merges, a single free record may remain for cotton. A skipped cotton candidate does not stop an exploration extra that can merge into its own compatible stack. There is no pending mailbox, later claim, or compensating mint for any candidate that cannot fit.

Current initial ceiling 50 active slots

The account format reserves 99 records, but the initialization instruction clamps capacity to 50.

Strict grass storage Matching headroom or one free record

The transaction fails atomically only when the grass reward can use neither form of storage.

Cotton storage Matching cotton headroom or the next free record

Cotton is attempted before the exploration extra, using its metadata-specific block-stack identity.

RECIPE 1025

Four cotton units and one dry-grass unit must match exactly

The current enabled recipe in table 222 has two block templates for order-independent matching: cotton block ID 48 with quantity four and dry-grass block ID 29 with quantity one. Its chain output is material item code 1025. The public material catalog maps that code to class fiber, forge use fabric, and render mode cloth. Plant fiber is no longer in the public material catalog; recipes 1003 and 2003 remain disabled so active identities do not shift.

Execution must also include at least one fuel index whose maximum heat tier reaches the recipe's minimum of one. Input and fuel indexes share one uniqueness set, so an index contributing dry grass to the recipe cannot also serve as fuel. A batch multiplier scales both template quantities, but the recipe still produces one material record whose volume is calculated from that output template and the batch's consumed-to-template input-volume ratio.

Verified input IDs 48 + 48 + 48 + 48 + 29

The chain matches packed block identifiers from authoritative backpack records.

Output identity Item code 1025

One quantity-bearing cotton-cloth material record is appended for the current single-output recipe.

Heat boundary Tier 1 · separate fuel

At least one unique fuel slot is required in addition to the five recipe inputs.

AUTHORITATIVE MATERIAL TRANSITION

Recipe execution consumes exact units and writes the resulting cloth

Before mutating the backpack, the Smelting Program validates its owner, capacity, every unique input and fuel index, exact quantities, heat tier, and the room available after partial or complete consumption and output insertion. It sums only the proportional input volume being consumed, excludes fuel volume, then asks the Backpack Program to consume those exact input quantities and one unit from each selected fuel stack.

For each active output, the program starts from that output's PDA template volume, scales it by batch multiplier and by the ratio of actual selected input volume to expected recipe-template input volume, then applies recipe yield and the current Smelting skill multiplier with integer arithmetic. For one default-volume cotton-cloth batch, the five-million template becomes 325,000 cubic millimetres at level zero or 487,500 at level ten. The current one-output recipe writes one cloth slot carrying that calculated batch volume.

Fiber recipe yield 650 bps

Applied to the scaled per-output PDA template before the skill factor, using integer division.

Skill output factor 10,000 to 15,000 bps

Level zero preserves the recipe output; levels one through ten add 5% extra output each.

Mutation scope Input units + one fuel unit out · cloth in

Partial stack updates, full removals, and output append occur inside one atomic transaction.

CLOTH INSIDE THE FORGE

The editor inherits rich material behaviour; the chain keeps a narrower aggregate proof

The forging page maps item code 1025 back to cotton cloth and asks Chunk.js for the baked cloth surface used by material swatches and the live workbench. Locally, each 14 by 10 by 14 component measures occupied cells, scales the selected slot's volume to the material actually present, multiplies that volume by density score, and uses the resulting mass weight across twelve attributes. Restored equipment rebuilds encoded geometry and RGB444 colors, then uses its cloth identity for wind motion; it does not retain the workbench material tile. Cloth painting and runtime flutter are presentation and design behaviour, not a chain simulation of fabric.

Forge submission takes whole selected material slots. The Backpack Program verifies that every index is a valid material, rejects duplicates, and checks selected volume, effective durability, and validated mass against the three NCF1 requirements. It then creates an immutable ForgedItem PDA containing the complete NCF1 bytes, consumes all selected slots, and appends one forged record pointing to that account. Neither account preserves the full input list, exact cloth provenance, or dye-to-paint relationship; the Backpack record keeps NCF1-derived volume and mass plus material-derived outcome fields and the 32-bit design hash.

Five flower-dye recipes are enabled, but the current verified world path has no native way to collect water block 17: water is unmineable, rule tables reject water drops, and no bucket instruction exists. The page therefore treats dye as an available recipe definition, not a complete world-harvest-to-dye loop.

Local component grid 14 × 10 × 14

Used volume follows occupied component cells before density-weighted inheritance.

Chain forge checks Volume + effective durability + mass

The current verifier checks three aggregate capacities across whole selected slots.

Dye status Recipes exist · collection loop incomplete

A verified native source for required water block 17 is not currently implemented.

DROP, CAPACITY, AND YIELD MATH

One fixed hash chooses the plant; ordered slots decide whether the reward survives

The first equation scopes cotton to eligible grass coordinates. The second models the strict base reward and ordered lossy extras. The third mirrors recipe 1025's exact input counts, per-output PDA volume baseline, selected-input ratio, and two-stage integer yield.

Cotton's deterministic rule interval

H = surfaceHeight(x,z); r = hashCoord3(seed,x,H+1,z,1200+201) mod 10000; cotton iff surfaceBlock=grass AND (waterLevel is null OR waterLevel<=H) AND treeBlock(x,H+1,z)=air AND 425<=r<455; P_roll(cotton | eligible grass) = (455-425)/10000 = 0.003

Rule 74 occupies thirty values in the shared ten-thousand-value band for salt 201. The 0.3% figure is the conditional hash share for an otherwise eligible grass face; it is not a fresh random chance per swing and not a percentage of every world block.

H
Canonical generated surface height at horizontal coordinate x,z.
r
Stable unsigned rule roll shared by rows using salt 201 at this coordinate.
425 <= r < 455
The half-open interval assigned to cotton in the current revision-2 table.

Strict support reward, then ordered stack-aware lossy extras

S1 = strictStore(S0,grass); A_cotton = D*canStore(S1,cotton[block=48,metadata=(74<<16)|12]); S2 = A_cotton ? store(S1,cotton) : S1; A_extra = E*canStore(S2,extra[block=dropId,metadata=0]); S_after = A_extra ? store(S2,extra) : S2

The mandatory grass reward first merges into compatible headroom or opens a record; if neither is possible, the whole transaction fails. D and E indicate an eligible cotton decoration and exploration extra. The lossy batch then attempts cotton and extra in order against the evolving Backpack state. Each may merge without increasing itemCount, each is skipped independently when it cannot fit, and failure of the cotton attempt does not stop the later extra attempt.

S0, S1, S2, S_after
Backpack state before the base reward, after strict grass, after the cotton attempt, and after the exploration-extra attempt.
D, E
Binary indicators for an eligible surface decoration and exploration extra.
A_cotton, A_extra
Whether each secondary candidate has matching stack headroom or can open a new record when its turn is evaluated.

Cotton-cloth inputs and per-output integer volume

N_cotton=4m; N_dryGrass=m; N_fuel>=1; inputIndexes intersect fuelIndexes = empty; b_skill=min(15000,10000+500L); V_expected=max(1,m*V_recipe); V_scaled=floor(max(1,V_template)*m*max(1,V_in)/V_expected); V_cloth=max(1,min(2^32-1,floor(floor(V_scaled*650/10000)*b_skill/10000)))

Batch multiplier m scales the quantities in recipe 1025's cotton and dry-grass templates, while every input and fuel index must remain unique. Fuel volume is not part of V_in. The program first scales this output's five-million-cubic-millimetre PDA template by the ratio between consumed and recipe-template input volume, then applies the 650-basis-point recipe yield and the 10,000-to-15,000 skill multiplier with integer division. It does not divide one aggregate result evenly among outputs.

m
Recipe batch multiplier; one batch consumes four cotton units and one dry-grass unit from unique selected indexes.
L
Current smelting level from zero through ten.
V_recipe, V_template, V_in, V_cloth
One batch's expected recipe-input volume, this output's PDA template volume, selected recipe-input volume, and the resulting cloth-record volume in cubic millimetres.

Every secondary reward write validates the backpack owner

Rust programs/nicechunk_backpack/src/state.rs
        Self::validate_owner(data, owner)?;

Owner validation is the stable boundary shared by every lossy reward implementation. In v4, the remaining routine evaluates optional rewards in order, fills matching 99-unit block-stack headroom first, skips only units that still do not fit, and updates aggregate mass only for stored units.

Verified inputs and every output are checked before Backpack mutation

Rust programs/nicechunk_smelting/src/lib.rs
    let validated_inputs = {
        let backpack_data = backpack.try_borrow_data()?;
        BackpackAccountView::validate_recipe_inputs(
            &backpack_data,
            owner.key,
            indexes,
            fuel_indexes,
            &recipe,
            multiplier,
        )?
    };

    let recipe_input_volume_mm3 = recipe_input_volume_mm3(&recipe);
    let mut output_volumes_mm3 = [0_u32; state::RECIPE_MAX_OUTPUTS];
    let mut output_quantities = [0_u32; state::RECIPE_MAX_OUTPUTS];
    for output_index in 0..recipe.output_count as usize {
        let output = &recipe.outputs[output_index];
        output_volumes_mm3[output_index] = smelting_recipe_output_volume_mm3(
            &recipe,
            output,
            validated_inputs.input_volume_mm3,
            recipe_input_volume_mm3,
            multiplier,
            skill_output_bps,
        )?;
        output_quantities[output_index] = smelting_output_quantity(
            &recipe,
            output,
            validated_inputs.consumed_input_units,
            multiplier,
            skill_output_bps,
        )?;
    }
    consume_backpack_resources(
        program_id,
        smelting_authority,
        owner,
        backpack,
        backpack_program,
        material_physics,
        indexes,
        fuel_indexes,
        &validated_inputs.consumption_quantities,
    )?;

Validation first reads the authoritative Backpack and calculates exact per-slot input quantities. The program then computes every active output's checked volume and quantity into fixed arrays. Only after all those fallible calculations succeed does it consume the exact input quantities plus one unit from each selected fuel stack; later append or progress failure still rolls the complete Solana transaction back.

Chunk.js weights inherited attributes by material actually used

JavaScript chunk.js/forge/forge-workbench.js
    inputVolumeMm3 = checkedSafeAdd(inputVolumeMm3, material.volumeMm3, "total forge input volume");
    const componentSolidCells = forgeSolidCellCount(component.solid);
    componentSolidCellCounts[index] = componentSolidCells;
    solidCellCount += componentSolidCells;
    const componentVolumeMm3 = Math.floor(material.volumeMm3 * componentSolidCells / FORGE_WORKBENCH_SOLID_CELL_COUNT);
    componentVolumesMm3[index] = componentVolumeMm3;
    usedVolumeMm3 = checkedSafeAdd(usedVolumeMm3, componentVolumeMm3, "used forge material volume");
    // With integer kg/m3 and mm3 inputs, this product is an exact microgram
    // count. The public density ceiling keeps the 24-component total inside
    // Number's safe-integer range; BigInt below preserves exact score weights.
    const massWeight = componentVolumeMm3 * material.profile.densityKgM3;
    componentMassWeights[index] = massWeight;
    massWeightTotal = checkedSafeAdd(massWeightTotal, massWeight, "forge material mass weight");
    for (let attributeIndex = 0; attributeIndex < FORGE_ATTRIBUTE_KEYS.length; attributeIndex += 1) {
      const key = FORGE_ATTRIBUTE_KEYS[attributeIndex];
      attributeTotals[attributeIndex] += BigInt(material.profile.attributes[key]) * BigInt(massWeight);

The local workbench derives twelve design attributes from occupied component cells and density-weighted used volume. This detailed inheritance explains the editor and exported design, but the chain stores only aggregate forge outcome fields and a 32-bit design hash.

IMPLEMENTATION EVIDENCE

Where these claims come from

Each claim is intentionally scoped to a concrete implementation path. These references are for verification, not decoration.

chunk.js/world/surface-decoration-rules.js

Defines the current cotton and five-color flower fixture rows, disjoint basis-point bands, flags, and generic rule compiler used by Chunk.js initialization and tests.

programs/nicechunk_chunk/src/state.rs

Validates the deployed SurfaceDecorationTable format and mirrors the stable hash, water, tree, surface, height, salt, and ordered interval matching.

programs/nicechunk_chunk/src/lib.rs

Shows canonical mining validation, strict support-block storage, cotton metadata packing, and decoration-before-exploration secondary reward ordering.

programs/nicechunk_backpack/src/state.rs

Implements strict and lossy backpack appends, exact Smelting stack consumption, dense capacity accounting, whole-slot forge consumption, and aggregate forge material checks.

src/data/smeltingRules.js

Publishes cotton cloth as four cotton plus one dry grass, item and recipe code 1025, fiber yield, cloth rendering mode, and twelve base attributes.

scripts/sync-smelting-recipes.ts

Encodes one quantity-bearing RecipeTable template per raw or material requirement and keeps disabled plant-fiber recipe identities inactive.

programs/nicechunk_smelting/src/state.rs

Allocates exact recipe quantities from unique input indexes, validates fuel indexes, projects Backpack output capacity after partial consumption, checks heat tier and packed block identifiers, and derives skill output basis points.

programs/nicechunk_smelting/src/lib.rs

Consumes validated recipe quantities and one unit per fuel index, calculates bounded output volume and quantity, appends material output, and awards Smelting progress atomically.

chunk.js/forge/forge-workbench.js

Calculates used component volume and density-mass-weighted local attribute inheritance for the NCF1 workbench.

forging/chain-adapter.js

Maps authoritative backpack material slots into the forge UI while filtering the retired plant-fiber item identity.

tests/smelting_rules.ts

Locks cotton and flower block IDs, exact cotton-cloth inputs, material output identity and volume template, dye inputs, and plant-fiber retirement.