Skip to content

Commit

Permalink
Merge pull request #20 from retraigo/item-config
Browse files Browse the repository at this point in the history
Create a getter and setter for items
  • Loading branch information
retraigo authored Nov 2, 2022
2 parents 6f3bd2c + 5f993a1 commit 5e186b6
Show file tree
Hide file tree
Showing 3 changed files with 97 additions and 33 deletions.
58 changes: 41 additions & 17 deletions mod.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,20 +3,44 @@
// This code was bundled using `deno bundle` and it's not recommended to edit it manually

class GachaMachine {
items;
tiers;
maxTier;
totalChance;
pool;
#items;
#tiers;
#maxTier;
#totalChance;
#pool;
constructor(items){
this.items = [];
this.tiers = [];
this.pool = [];
this.maxTier = 1;
this.totalChance = 0;
this.#items = [];
this.#maxTier = 1;
this.#pool = [];
this.#tiers = [];
this.#totalChance = 0;
this.#configTiers(items);
this.#configItems(items);
}
get items() {
return this.#items;
}
set items(data) {
this.#items = [];
this.#maxTier = 1;
this.#pool = [];
this.#tiers = [];
this.#totalChance = 0;
this.#configTiers(data);
this.#configItems(data);
}
get maxTier() {
return this.#maxTier;
}
get pool() {
return this.#pool;
}
get tiers() {
return this.#tiers;
}
get totalChance() {
return this.#totalChance;
}
#configTiers(items) {
let i = 0;
const tiers = new Set();
Expand All @@ -25,7 +49,7 @@ class GachaMachine {
i += 1;
}
for (const tier of tiers){
if (tier > this.maxTier) this.maxTier = tier;
if (tier > this.maxTier) this.#maxTier = tier;
}
const itemsInTier = new Uint8Array(this.maxTier + 1);
const totalChanceInTier = new Uint8Array(this.maxTier + 1);
Expand All @@ -36,33 +60,33 @@ class GachaMachine {
i += 1;
}
for (const tier1 of tiers){
this.tiers.push({
this.#tiers.push({
tier: tier1,
totalChance: totalChanceInTier[tier1],
items: itemsInTier[tier1]
});
}
this.pool = Array.from(tiers);
this.#pool = Array.from(tiers);
}
#configItems(items1) {
let i1 = 0;
let cumulativeChance = 0;
while(i1 < items1.length){
cumulativeChance += items1[i1].chance;
this.items.push({
this.#items.push({
result: items1[i1].result,
chance: items1[i1].chance,
cumulativeChance: cumulativeChance,
tier: items1[i1].tier || 1
});
i1 += 1;
}
this.totalChance = cumulativeChance;
this.#totalChance = cumulativeChance;
}
get(count = 1) {
if (count === 1) {
return [
GachaMachine.rollWithBinarySearch(this.items, this.totalChance),
GachaMachine.rollWithBinarySearch(this.items, this.totalChance)
];
}
const result = new Array(count);
Expand All @@ -79,7 +103,7 @@ class GachaMachine {
}
if (count === 1) {
return [
GachaMachine.rollWithBinarySearch(this.items, this.totalChance),
GachaMachine.rollWithBinarySearch(this.items, this.totalChance)
];
}
const tempItems = this.items.slice(0);
Expand Down
55 changes: 39 additions & 16 deletions mod.ts
Original file line number Diff line number Diff line change
Expand Up @@ -47,24 +47,48 @@ export interface ComputedTierData {
* A gacha machine for weighted selection.
*/
export class GachaMachine<ItemType> {
items: ComputedGachaData<ItemType>[];
tiers: ComputedTierData[];
maxTier: number;
totalChance: number;
pool: number[];
#items: ComputedGachaData<ItemType>[];
#tiers: ComputedTierData[];
#maxTier: number;
#totalChance: number;
#pool: number[];
/**
* Create a new gacha machine for weighted selection.
* @param items Array of items to roll from.
*/
constructor(items: GachaData<ItemType>[]) {
this.items = [];
this.tiers = [];
this.pool = [];
this.maxTier = 1;
this.totalChance = 0;
this.#items = [];
this.#maxTier = 1;
this.#pool = [];
this.#tiers = [];
this.#totalChance = 0;
this.#configTiers(items);
this.#configItems(items);
}
get items(): ComputedGachaData<ItemType>[] {
return this.#items;
}
set items(data: GachaData<ItemType>[]) {
this.#items = [];
this.#maxTier = 1;
this.#pool = [];
this.#tiers = [];
this.#totalChance = 0;
this.#configTiers(data);
this.#configItems(data);
}
get maxTier() {
return this.#maxTier;
}
get pool() {
return this.#pool;
}
get tiers() {
return this.#tiers;
}
get totalChance() {
return this.#totalChance;
}
#configTiers(items: GachaData<ItemType>[]) {
let i = 0;
const tiers = new Set<number>();
Expand All @@ -73,7 +97,7 @@ export class GachaMachine<ItemType> {
i += 1;
}
for (const tier of tiers) {
if (tier > this.maxTier) this.maxTier = tier;
if (tier > this.maxTier) this.#maxTier = tier;
}
const itemsInTier = new Uint8Array(this.maxTier + 1);
const totalChanceInTier = new Uint8Array(this.maxTier + 1);
Expand All @@ -84,28 +108,28 @@ export class GachaMachine<ItemType> {
i += 1;
}
for (const tier of tiers) {
this.tiers.push({
this.#tiers.push({
tier: tier,
totalChance: totalChanceInTier[tier],
items: itemsInTier[tier],
});
}
this.pool = Array.from(tiers);
this.#pool = Array.from(tiers);
}
#configItems(items: GachaData<ItemType>[]) {
let i = 0;
let cumulativeChance = 0;
while (i < items.length) {
cumulativeChance += items[i].chance;
this.items.push({
this.#items.push({
result: items[i].result,
chance: items[i].chance,
cumulativeChance: cumulativeChance,
tier: items[i].tier || 1,
});
i += 1;
}
this.totalChance = cumulativeChance;
this.#totalChance = cumulativeChance;
}
/**
* Roll items from the gacha machine.
Expand Down Expand Up @@ -136,7 +160,6 @@ export class GachaMachine<ItemType> {
}
/**
* Roll unique items from the gacha machine.
* WARNING: This feature is currently unstable.
* @param count Number of items to roll.
* @returns `count` number of items from the items fed to the constructor.
* @example
Expand Down
17 changes: 17 additions & 0 deletions test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -88,6 +88,23 @@ Deno.test({
},
});

Deno.test({
name: `Machine can be updated by just setting machine.items after initialization.`,
fn() {
const machine = new GachaMachine(testData);

const machine2 = new GachaMachine(testData.slice(0, 3));

machine.items = testData.slice(0, 3);

assertEquals(machine.items, machine2.items, "Items are not equal.");
assertEquals(machine.tiers, machine2.tiers, "Tiers are not equal.");
assertEquals(machine.totalChance, machine2.totalChance, "totalChance are not equal.");
assertEquals(machine.maxTier, machine2.maxTier, "maxTier are not equal.");
assertEquals(machine.pool, machine2.pool, "pool are not equal.");
},
});

/*
Deno.test({
name: `${sortedTestData[0].chance} in ${testData.reduce((acc, val) => acc + val.chance, 0)} rolls return a ${sortedTestData[0].result}?`,
Expand Down

0 comments on commit 5e186b6

Please sign in to comment.