Skip to content

Random Item Generation

Belongs to: Server Owner Guide · Related: Quality & Display · Section · Affix

QI can randomly generate equipment just like MMOItems: roll a Tier by quality weight → compute affix slots by capacity → roll affixes from affix pools → assemble the item. Command entry: /qi generate.


1. Command Usage

CommandDescription
/qi generate [tier] [type] [amount]Randomly generate an item and put it in the inventory
/qi generate preview [tier] [type]Only preview the generation result, do not actually create it
/qi generate poolsList the available affix pools

All parameters can be omitted (if left blank, a random Tier and the default pool are used). See Commands.


2. Generation Flow

1. Roll Tier        ItemTierRarityRoller —— weighted random based on each tier's generation.chance
2. Compute capacity TierCapacityCalculator —— derive the slot count from the tier's capacity parameters
3. Distribute       AffixRoller.distributeCapacity —— evenly split the capacity across the affix pools
4. Roll affixes     AffixRoller.rollFromPool —— roll affixes from each pool by its capacity
5. Merge            take the first prefix, take the first suffix, merge all Lore
6. Create item      generate amount items, write seed / tier / quality / template tags
7. Grant            if a player is specified, place into inventory; overflow drops naturally

3. Capacity Calculation

The capacity parameters come from the Tier's generation.capacity (see Quality):

capacity = base + (scale × rand) + (spread × rand) + (maxSpread × rand)
         (each rand is an independent [0,1) random; the result is floored, never below 0)

Examples:

COMMON   { base:2, scale:3 }                 → 2 + rand(0~3)            = [2,4]
LEGENDARY{ base:10, scale:5, spread:3, maxSpread:2 } → 10 + each term random = [10,20]

4. Weighted Tier Roll

candidates = all tiers with generation.chance > 0
total = sum of all chance values
r = random × total
subtract each chance one by one; when r < 0 the corresponding tier is hit

Example: COMMON=50, UNCOMMON=30, RARE=15, EPIC=4, LEGENDARY=1, r=45 → hits EPIC.


5. Affix Pool Roll

Each pool (a Section) is rolled according to its type:

Section TypeRoll Method
weight_join / affix_poolWeighted without replacement, roll amount entries
quality_poolFind the sub-pool by the current tier, then roll it as a weight_join
OthersTreat as a single-entry pool, take its prefix/suffix/lore

The affix pool is affix_pool by default; use /qi generate pools to view them all.

Two-Level Routing of Quality Pools

yaml
quality_pool_damage:
  type: quality_pool
  common: "pool_damage_common"     # tier=COMMON → use this sub-pool
  rare: "pool_damage_rare"

pool_damage_rare:
  type: weight_join
  values:
    - "3::+8 Damage"
    - "5::+10 Damage"

When generating a RARE item, quality_pool_damage finds rarepool_damage_rare → rolls from it with weights.


6. Developer API

kotlin
RandomItemGenerator.generate(random, Options(
    tierId = "LEGENDARY",            // force the tier (random if blank)
    itemType = "sword",              // force the type
    templateId = "legendary_sword",  // use a template item
    poolIds = listOf("affix_pool"),  // affix pools
    amount = 3,                      // amount
    giveTo = player,                 // grant directly (overflow drops)
)): GenerationResult

RandomItemGenerator.preview(random, options): String   // text preview

Returns:

kotlin
data class GenerationResult(
    val items: List<ItemStack>,
    val tier: ItemTier?,
    val affixResults: List<AffixRoller.AffixResult>,
    val summary: String,             // human-readable summary
)

7. Item Refresh Service

A companion capability related to random generation: after you change set / Tier / template configuration, re-render the items already on the players. QinhItemRefreshService:

kotlin
QinhItemRefreshService.refreshOnlinePlayers(): RefreshReport
QinhItemRefreshService.refreshPlayer(player): RefreshReport
QinhItemRefreshService.refreshEquipment(player): RefreshReport
QinhItemRefreshService.refreshItems(items): RefreshReport

The corresponding command is /qi refresh (and all / inventory / armor / equipment / hand), see Commands. Refresh = call assembly().rebuild() + variables().refresh() on each QI item, preserving the instance / seed and only updating the display.


Next Steps