use of buildcraft.api.transport.pipe.PipeEventItem.ItemEntry in project BuildCraft by BuildCraft.
the class PipeBehaviourDiamondItem method split.
@PipeEventHandler
public void split(PipeEventItem.Split split) {
EnumFacing[] allSides = split.getAllPossibleDestinations().toArray(new EnumFacing[0]);
if (allSides.length == 0 || allSides.length == 1) {
// Nothing to split
return;
}
ItemEntry[] items = split.items.toArray(new ItemEntry[0]);
split.items.clear();
// Note that the order doesn't matter
for (ItemEntry item : items) {
int[] countPerSide = new int[allSides.length];
int totalCount = 0;
for (int s = 0; s < allSides.length; s++) {
int offset = FILTERS_PER_SIDE * allSides[s].ordinal();
for (int i = 0; i < FILTERS_PER_SIDE; i++) {
ItemStack compareTo = filters.getStackInSlot(offset + i);
if (compareTo.isEmpty())
continue;
if (StackUtil.isMatchingItemOrList(compareTo, item.stack)) {
int count = compareTo.getCount();
totalCount += count;
countPerSide[s] += count;
}
}
}
if (totalCount == 0) {
totalCount = allSides.length;
Arrays.fill(countPerSide, 1);
} else {
int hcf = countPerSide[0];
for (int c : countPerSide) {
hcf = MathUtil.findHighestCommonFactor(hcf, c);
}
if (hcf != 1) {
totalCount /= hcf;
for (int i = 0; i < countPerSide.length; i++) {
countPerSide[i] /= hcf;
}
}
}
/* If the stack count is divisible by the possible directions then we can just split the stack up evenly -
* making the distribution perfect. */
ItemEntry[] entries = new ItemEntry[allSides.length];
ItemStack toSplit = item.stack;
if (toSplit.getCount() >= totalCount) {
int leftOver = toSplit.getCount() % totalCount;
int multiples = (toSplit.getCount() - leftOver) / totalCount;
for (int s = 0; s < allSides.length; s++) {
ItemStack toSide = toSplit.copy();
toSide.setCount(countPerSide[s] * multiples);
entries[s] = new ItemEntry(item.colour, toSide, item.from);
List<EnumFacing> dests = new ArrayList<>(1);
dests.add(allSides[s]);
entries[s].to = dests;
}
toSplit.setCount(leftOver);
}
if (!toSplit.isEmpty()) {
int[] randLookup = new int[totalCount];
int j = 0;
for (int s = 0; s < allSides.length; s++) {
int len = countPerSide[s];
Arrays.fill(randLookup, j, j + len, s);
j += len;
}
while (!toSplit.isEmpty()) {
// Pick a random number between 0 and total count.
int rand = split.holder.getPipeWorld().rand.nextInt(totalCount);
int face = randLookup[rand];
if (entries[face] == null) {
ItemStack stack = toSplit.copy();
stack.setCount(1);
ItemEntry entry = new ItemEntry(item.colour, stack, item.from);
List<EnumFacing> dests = entry.to = new ArrayList<>(1);
dests.add(allSides[face]);
entries[face] = entry;
} else {
entries[face].stack.grow(1);
}
toSplit.shrink(1);
}
}
for (int s = 0; s < allSides.length; s++) {
ItemEntry entry = entries[s];
if (entry == null) {
continue;
}
split.items.add(entry);
}
}
}
Aggregations