Documentation

Machine Type craft template

Build your own smart contract for Machine Type Vessel tokens. Deploy a machine, then attach it when claiming or via setMachineHolder.

Machine Crafts resolve their payload through an external machine contract. That contract implements IMachine — primarily craftToPayload(tokenId) and name() — and may read Vessel state through IVessel to transform or generate bytes on-chain. Machines let a Craft become more than stored bytes: they allow behavior.

Use the template below as a starting point. Pass the Vessel contract address into the constructor, implement craftToPayload with your logic, then supply the deployed machine address when claiming a Machine Craft or when calling setMachineHolder. The machine address must be a deployed contract (non-zero code); address(0) reverts.

Published presets

MachineWhat it does
RouterDefault machine at claim. Rotates among registered machines as mint progress increases.
HyperportalSamples Terraforms heightmaps on-chain and resamples them into the Craft’s byte capacity.
EntropyGenerates a fresh byte pattern from tokenId and block.number — output changes every block.
  • Router — set as the default Machine at claim. blocksPerStep = 10000 − claimedCount (minimum 1); the active child machine rotates every blocksPerStep blocks. Output is capped to tokenId bytes.
  • Entropy — keccak256(tokenId, block.number) expands into a full-capacity random byte field. The image changes as Ethereum produces blocks.
  • Hyperportal — reads Terraforms 32×32 heightmaps, scales heights 0–9 → 0–255, and resamples into a square then trims to token capacity. Holders can call setCraftToChosenParcel to pick a Terraforms parcel.

Explore community machines

Before you build — or while you iterate — learn from machine types that other people have already deployed. machine.thevessel.fun is a place to browse, study, and explore community-built machines. Core sources also live in the public contracts repo under Machines/.

Required interface

  • IMachine.craftToPayload(uint256 tokenId) → bytes — dynamic payload for that Craft
  • IMachine.name() → string — human-readable machine label
  • IVessel — read Vessel material your machine needs (extend with craftToRole, craftToLocked, etc.)

Template

GenericMachine.sol
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.20;

interface IMachine {
    function craftToPayload(uint256 tokenId)
        external
        view
        returns (bytes memory);

    function name()
        external
        view
        returns (string memory);
}

interface IVessel {
    function craftToPayload(uint256 tokenId)
        external
        view
        returns (bytes memory);

    // Add any other read functions your Machine needs.
    // Example:
    // function craftToRole(uint256 tokenId) external view returns (uint8);
    // function craftToLocked(uint256 tokenId) external view returns (bool);
}

contract GenericMachine is IMachine {
    IVessel public immutable vessel;
    string public constant MACHINE_NAME = "Generic Machine";

    constructor(address vesselAddress) {
        vessel = IVessel(vesselAddress);
    }

    function name() external pure returns (string memory) {
        return MACHINE_NAME;
    }

    function craftToPayload(uint256 tokenId)
        external
        view
        returns (bytes memory)
    {
        // Insert custom logic here.
        // You might generate entirely new data,
        // or read and reinterpret onchain material.
        // return _transform(basePayload);

        return bytes("");
    }
}